Formulaire de recherche polyvalent sur la base d'une requête enregistrée

Un formulaire tout-en-un : ajout, modification, suppression, recherche multicritère

Claude LELOUP

Des tutoriels traitant du sujet sur DVP :

RECHERCHE MULTI-CRITERES de cafeine ;

Création d'un formulaire de recherche multicritère de jeannot45 ;

Formulaire de recherche prêt à l'emploi de loufab ;

Un formulaire de recherche basé sur la technique du père/fils de Mandresy Rabenja (madefemere) et Claude Leloup.

Commentez

- Titre : Formulaire de recherche polyvalent sur la base d'une requête enregistrée

- Auteur : Claude LELOUP

- Parution : 25 septembre 2014

- Mise à jour : 11 février 2016

- Public visé :

- Licence : Copyright ® 2014 Claude Leloup. Aucune reproduction, même partielle, ne peut être faite de ce site et de l'ensemble de son contenu : textes, documents, images, etc. sans l'autorisation expresse de l'auteur. Sinon vous encourez selon la loi jusqu'à trois ans de prison et jusqu'à 300 000 € de dommages et intérêts.

Sommaire

- I. L'objectif

- II. Étape 1 : construire une requête qui sélectionne toutes les colonnes souhaitées

- III. Étape 2 : affecter cette requête comme source du formulaire

- IV. Étape 3 : ajouter dans le formulaire, les contrôles qui vont servir à exprimer les choix

- V. Étape 4 : ouvrir le formulaire et compléter la requête

- V-A. Sept clics pour construire la référence à un contrôle du formulaire

- V-B. Construction des critères de sélection de la requête

- V-B-1. Pour un filtre du type « Zone de liste modifiable »

- V-B-2. Pour un filtre du type « Zone de texte »

- V-B-3. Pour un filtre du genre « Période comprise entre deux dates »

- VI. Étape 5 : faire réagir le formulaire lorsque l'utilisateur a opéré un choix

- VII. Étape 6 : des petits bonus pour faciliter la tâche de l'utilisateur

- VII-A. Remettre un filtreXXX à Null en un double-clic

- VII-B. Un clic sur le bouton « Afficher tout » pour remettre tous les filtres à Null

- VII-C. Afficher le nombre d'occurrences dans la sélection

- VII-D. Éviter l'incohérence des dates définissant la période

- VIII. Étape 7 : éventuellement, incorporer le SQL de la requête dans le formulaire

- IX. En guise de conclusion

- X. Remerciements

I - L'objectif

Une zone de choix restée « Null » (situation à l'ouverture), signifie : pas de filtrage sur la base de ce critère.

On veut pouvoir filtrer le résultat sur la base d'un titre complet, choisi dans la liste (recherche stricte) ou d'une chaîne de caractères qui serait contenue dans les titres (recherche étendue).
On veut limiter la sélection aux items de la liste (recherche stricte).

On veut faire une recherche étendue sur la chaîne de caractères.

On veut opérer une recherche entre deux dates.

Un clic pour rétablir la liste complète.

Un double-clic sur à provoque la remise à « Null » de ce contrôle.

II - Étape 1 : construire une requête qui sélectionne toutes les colonnes souhaitées

III - Étape 2 : affecter cette requête comme source du formulaire

Ce qui nous donne :

IV - Étape 3 : ajouter dans le formulaire, les contrôles qui vont servir à exprimer les choix

Ces contrôles sont indépendants (propriété « Source » vide).

Pour simplifier le peu de code VBA qui sera nécessaire, on « normalise » le nom de ces contrôles. Dans l'exemple, leur nom commence par « filtre ».

V - Étape 4 : ouvrir le formulaire et compléter la requête

Nous allons construire chacun des critères en nous référant au contenu (Null ou choisi) des contrôles filtreXXXX du formulaire fRecherche.

V-A - Sept clics pour construire la référence à un contrôle du formulaire

Affichez la requête en mode construction.

Placez le curseur de la souris dans la cellule qui correspond au critère de sélection de la colonne.

Cliquez droit et dans la petite fenêtre qui s'ouvre, cliquez sur le générateur d'expressions (Créer…)

et laissez-vous guider par votre intuition…

V-B - Construction des critères de sélection de la requête

V-B-1 - Pour un filtre du type « Zone de liste modifiable »

Une zone de liste modifiable contient une propriété « ListIndex » qui renseigne la position de l'item que l'utilisateur a choisi.

Dans ce contexte, Access commence sa numérotation à zéro.

Dans notre exemple, si l'utilisateur a choisi le premier item de la liste des titres Formulaires!fRecherche!filtreTitre.ListIndex vaut 0 ; s'il choisit le quatrième, cela vaut 3 ; tant qu'il n'a pas choisi un élément de la liste, la propriété vaut -1.

Si l'on considère individuellement la colonne « Titre », plusieurs cas peuvent se présenter :

Le contrôle filtreTitre contient

C'est-à-dire

.ListeIndex vaut

La requête doit ramener

ACV dans le monde industriel

Un élément de la liste.

>=0

L'enregistrement qui contient exactement le texte.

du

Une chaîne qui ne correspond pas à un titre.

-1

Tous les enregistrements dont le titre contient la chaîne « du ».

Null

Pas de choix.

-1

Tous les enregistrements quel que soit leur titre.

Schématiquement :

Pour exprimer « ceux qui ressemblent à Formulaires!fRecherche!filtreTitre », nous allons utiliser les expressions régulières, si la notion ne vous est pas familière, voyez l'aide Access :

- enfoncez <CTRL + G> pour ouvrir la fenêtre d'exécution ;

- saisissez « like » et enfoncez F1, l'aide Access s'affiche

Après lecture, quelques essais et le souvenir de vos cours d'anglais, vous comprendrez que la syntaxe

va ramener :

Si filtreTitre contient

La requête va ramener

ACV dans le monde industriel

La seule occurrence qui contient ce titre complet.

N.B.

« comme "*" & "ACV dans le monde industriel" & "*" » est synonyme de « = "ACV dans le monde industriel" ».

du

Les occurrences dont le titre contient du:

ACV dans le monde industriel ;
L'aspect social du dd ;
…

Null

Tous les enregistrements quel que soit leur titre.

N.B.

« Comme "*" & Null & "*" » est synonyme de « Comme "*" ».

OK, on sait comment écrire les mots,

construisons maintenant la phrase !

Retour dans l'aide Access, pour se documenter sur la fonction IIF() :

Souvent, ce qui est « virgule » du côté où Access parle anglais, devient « point-virgule » là où il s'exprime en français :

En résumé, on retient ceci :

… enfin dans notre exemple :

Pour les autres filtres du type « Zone de liste modifiable », on procède par analogie (que leur propriété soit « Limiter à liste » ou non).

V-B-2 - Pour un filtre du type « Zone de texte »

Dans le cas d'un filtre de type « Zone de texte », on utilisera la fonction EstNull() - IsNull() du côté ‘ricain - pour exprimer le critère :

V-B-3 - Pour un filtre du genre « Période comprise entre deux dates »

L'idée est d'avoir deux filtres : l'un pour exprimer « à partir du » et l'autre « jusqu'au ».

Dans le critère de la requête, on exprime qu'il faut ramener les enregistrements dont la date est

plus grande ou égale à « à partir de » et plus petite ou égale à « jusqu'au »

Quand il s'agit de comparer une expression à une valeur de type Date, on ne peut pas utiliser le modèle (pattern) « "*" » pour exprimer « n'importe quelle valeur ».

Ceci par exemple ne ramènerait rien si filtreDu avait une valeur Null :

>=VraiFaux(EstNull([Formulaires]![fRecherche]![filtreDu]);"*";[Formulaires]![fRecherche]![filtreDu])

Qu'à cela ne tienne, on va ruser :

- si Access réclame une « vraie date » comme point de départ, on lui dira de comparer par exemple au 1er janvier 1900 pour le cas où filtreDu est Null et au 1er janvier 2100 pour le cas où filtreAu est Null.

Le raisonnement vaut pour chaque filtre pris individuellement.
L'utilisateur peut évidemment conjuguer plusieurs choix simultanés pour mieux cibler sa recherche.

VI - Étape 5 : faire réagir le formulaire lorsque l'utilisateur a opéré un choix

À chaque événement « Après mise à jour » des contrôles « filtrexxx », nous provoquons l'actualisation du formulaire : on le force à relire sa source :

Private Sub filtreTitre_AfterUpdate()
Me.Requery
End Sub

Private Sub filtreAuteur_AfterUpdate()
Me.Requery
End Sub

Private Sub filtreSujet_AfterUpdate()
Me.Requery
End Sub

Private Sub filtreSupport_AfterUpdate()
Me.Requery
End Sub

Private Sub FiltreResume_AfterUpdate()
Me.Requery
End Sub

Private Sub filtreDu_AfterUpdate()
Me.Requery
End Sub

Private Sub filtreAu_AfterUpdate()
Me.Requery
End Sub

VII - Étape 6 : des petits bonus pour faciliter la tâche de l'utilisateur

VII-A - Remettre un filtreXXX à Null en un double-clic

Un double-clic sur un contrôle « filtrexxx » provoque sa remise à Null :

Private Sub RaZ()
Me.ActiveControl = Null
Me.Requery
End Sub

Private Sub filtreTitre_DblClick(Cancel As Integer)
RaZ
End Sub

Private Sub filtreAuteur_DblClick(Cancel As Integer)
RaZ
End Sub

Private Sub filtreSujet_DblClick(Cancel As Integer)
RaZ
End Sub

Private Sub filtreSupport_DblClick(Cancel As Integer)
RaZ
End Sub

Private Sub FiltreResume_DblClick(Cancel As Integer)
RaZ
End Sub

Private Sub filtreDu_DblClick(Cancel As Integer)
RaZ
End Sub

Private Sub filtreAu_DblClick(Cancel As Integer)
RaZ
End Sub

VII-B - Un clic sur le bouton « Afficher tout » pour remettre tous les filtres à Null

Private Sub BtTout_Click()
Dim ctl As Control
For Each ctl In Me.Controls
If Left(ctl.Name, 6) = "filtre" Then
Me(ctl.Name) = Null
End If
Next ctl
Me.Requery
End Sub

VII-C - Afficher le nombre d'occurrences dans la sélection

Et tant qu'à faire, respectons l'orthographe :

VII-D - Éviter l'incohérence des dates définissant la période

Private Sub filtreDu_BeforeUpdate(Cancel As Integer)
If Not IsNull(Me.filtreAu) And Me.filtreAu < Me.filtreDu Then
MsgBox "Période incohérente !", vbCritical
Cancel = True
Me.Undo
End If
End Sub

Private Sub filtreAu_BeforeUpdate(Cancel As Integer)
If Not IsNull(Me.filtreDu) And Me.filtreAu < Me.filtreDu Then
MsgBox "Période incohérente !", vbCritical
Cancel = True
Me.Undo
End If
End Sub

VIII - Étape 7 : éventuellement, incorporer le SQL de la requête dans le formulaire

Comme source du formulaire, on peut éventuellement remplacer le nom de la requête enregistrée par son SQL.

Personnellement, je ne le fais pas, car cette requête enregistrée peut aussi servir comme source d'un état s'il s'avère utile d'imprimer la sélection affichée.

(Un exemple a été ajouté dans la base de données.)

IX - En guise de conclusion

Si vous avez des remarques ou des commentaires sur le contenu de cet article, faites-les dans le fil de cette discussion : Commentez  .

La base de données qui a servi à la mise au point.

X - Remerciements

Merci à Arkham46 qui a vérifié la technique de cet article.

Merci à milkoseck qui en a vérifié l'orthographe.

Merci à vous qui avez lu le résultat.