Créer plusieurs PDF à partir d’un état Access

Ces articles pourraient également vous intéresser...

67 réponses

  1. lourme dit :

    bonjour

    dans mon état je voudrais ajouter un total dans mon pied de groupe, en focntion d’un critère particulier

    nom table : tabtri
    nom zone à cumuler : capon
    nom zone à tester : bor

    je veux cumuler capon si bor = “CC”
    j’ai donc testé un SomDom mais je ne trouve pas la bonne syntaxe.

    merci d’avance pour ton aide…. sinon pour le reste de la génération des Pdf, tout est ok

    cordilement

    • Hervé Inisan dit :

      Sur le principe, le calcul serait quelque chose comme :

      A placer dans une zone de texte, sur l’état.

  2. Hippone dit :

    Bonjour,

    Peux t’on avoir le code complet avec les fonctions, je galère depuis plusieurs jours le code ne fonctionne pas.

    J’ai bien tout vérifier mais il semble que quelque chose cloche, j’ai mis la cible vers mon bureau “C:\Users\soub6256\Desktop\Nouveau dossier” mais rien ne ce passe le ossier cible reste vide.

    J’ai mis en en ‘ Nom de base du fichier PDF à créer
    strFichier = “C:\Users\soub6256\Desktop\Nouveau dossier”

    Merci pour votre aide

    • Hervé Inisan dit :

      Le chemin du fichier serait sans doute plutôt comme ceci :

      avec :

      • Test : le nom d’un dossier existant sur le Bureau Windows.
      • Document.pdf : le nom du document à créer

      Si j’ai un moment, je posterai un exemple plus détaillé… ;)

  3. atulinde uzam dit :

    Très bien c’est ça notre soucis

  4. Hervé Inisan dit :

    lourme > Des cycles Démarrage/Arrêt répétés peuvent entraîner des problèmes de timeout, ou de fuites de mémoire, par exemple. Est-ce qu’il n’y a pas moyen de lancer Access et de faire tous les traitements dans une seule session ?

  5. lourme dit :

    Bonjour

    je génère un certain nombre de documents pdf (filtres différents) via des macros que je lance depuis un .exe en prenat soin de faire un quitt de access entre chaque macro….

    cependant j’ai parfois (pas toujours au même stade…) un message d’erreur : 3035 ressources systèmes insuffisantes alors que rien d’autre ne tourne sur mon PC en même temps…

    y a t’il une solution ? pourqoui le plantage n’intervient pas toujours au même moment voire parfois pas du tout ?

    merci d’avance

    cdt

  6. Hervé Inisan dit :

    lourme > Oui : il suffit d’écrire {0}{1} (sans espace entre les 2 paramètres).

  7. lourme dit :

    Bonjour

    petite question
    voici ce que j’ai codé :
    strFichier = “K:LilleGGVIEMOA_LILLE1_MOA_GC_BO_MVSMOA_GC_BO_MVS_GANPATProjetsRemu Gan Pat 2013Tableaux de comm” _
    & rst(“cpta”) & “Inspection {0} {1}.pdf” où {0} est le nom et {1} le prénom….

    y a t’il une astuce pour supprimer les blancs entre les deux à l’arrivée ?

    merci d’avance

    cordialement

  8. Hervé Inisan dit :

    lourme > Le tri d’une table n’a pas d’intérêt réel (la table est seulement un “entrepôt” pour stocker des données brutes). Et il ne peut y avoir qu’un tri à la fois sur une table, qui annule les autres (comme dans Excel). En résumé : je n’utilise strictement jamais le tri d’une table. ;)

    Par contre, la bonne idée est de construire justement une requête reposant sur cette table, et de définir le tri dans la requête. Ce tri sera toujours exécuté, et toujours fiable. Et on peut avoir plusieurs requêtes avec des tris différents. Il suffit ensuite de construire les états à partir de ces requêtes (si la requête est triée, l’état l’est aussi nécessairement).

  9. lourme dit :

    Bonjour

    tout marche pour le mieux …. ou presque

    quand j’importe mon fichier EXCEL trié, les enregistrements dans ma table ACCESS ne sont pas dans le même ordre !!!

    Comment coder un tri dans ma macro avant d’appliquer ma génération de pdf ? est ce que je peux trier ma tabvle access une fois pour toute avant de démarrer mes requêtes ?

    merci d’avance

    cdt

  10. Hervé Inisan dit :

    debuvba > Je ne peux malheureusement pas aider chaque visiteur du site en particulier, ça demanderait trop de temps. ;-)

    Par contre, je conseillerais de suivre les étapes pas à pas, très précisément. Et s’il y a des choses qui ne marchent pas, de reposter le problème détaillé ici, ou sur les forums du site.

  11. debuvba dit :

    Bonsoir,

    Serait ce possible de vous joindre en prive je debute en vba et je ne parvient pas a avoir mes pdf en appliquant ces codes. Je dois sauter une etape ou ne pas avoir compris qqch…

  12. Hervé Inisan dit :

    lourme > La deuxième condition a une valeur fixe, il n’est pas nécessaire d’y faire une concaténation. Elle peut donc déjà se simplifier en :

    (s’il y a des apostrophes, c’est que Index est un champ Texte ?)

    Ensuite, pour une concaténation globale, on peut faire :

  13. lourme dit :

    Bonjour

    j’ai un filtre dans une procédure qui est codé comme suit :
    strFiltre = “[agdc] = ‘” & rst(“agdc”) & “‘”

    Je voudrais ajouter une deuxième condition
    strFiltre = “[index] = ” & “’2′”

    Quelle est la bonne syntaxe pour concaténer ces deux conditions sur le filtre ?

    Merci d’avance

  14. Hervé Inisan dit :

    lourme > A ma connaissance, le générateur de PDF d’Access n’a pas d’options de ce type (PDFCreator aurait des méthodes PDFSigning qui pourraient faire l’affaire).

  15. lourme dit :

    Bonjour

    petite question subsidiaire lors de la génération automatique des pdf, y a t’il moyen de protéger les pdf générés (mot de passe ?)

    comment coder cela ?

    merci d’avance

  16. Hervé Inisan dit :

    julien > Il faudrait dans ce cas modifier la variable strFiltre, du genre :

    J’ai supposé que ref était un champ numérique. S’il s’agit d’un champ Texte, voir les conversations plus haut.

  17. julien dit :

    Bonjour,
    merci pour ce code, cependant j’aimerais pouvoir filtrer mes enregistrements à exporter en PDF en se basant sur des paramètres à saisir dans un formulaire. Par exemple de la réf. 20 à 30 etc… et je n’y arrive pas pour le moment !
    merci pour votre aide.

  18. Hervé Inisan dit :

    lourme > Super !

  19. lourme dit :

    Bonjour

    c’est parfait…..

    merci pour tout

    cdt

  20. Hervé Inisan dit :

    lourme > J’ai retesté : effectivement, comme je le disais plus haut, c’est la fonction Format() qui est inutile et qui fausse la valeur. Il suffit d’insérer z8 directement, de cette manière :

    Accessoirement, comme cpta est également injecté dans la chaîne, ce serait plus simple de lui mettre un “marqueur” dans strFichier (par exemple {2}), et d’écrire ensuite :

    … de façon à éviter la concaténation.

  21. lourme dit :

    bonjour

    oui z8 est défini en texte et

    voici ce que j’ai codé :
    strFichier = “K:LilleGGVIEMOA_LILLE1_MOA_GC_BO_MVSMOA_GC_BO_MVS_GANPATProjetsRemu Gan Pat 2013Tableaux de comm” _
    & rst(“cpta”) & “Inspection {0} – {1}.pdf”

    ‘ Le nom du fichier varie en fonction de la personne
    strFichierPDF = StringFormat(strFichier, _
    Format(rst(“z8″)), _
    rst(“nominsp”))

    ai je une erreur de syntaxe ?

    merci

  22. Hervé Inisan dit :

    lourme > J’ai aussi repointé StringFormat(). Je ne vois pas d’effet de bord. Par exemple, dans la fenêtre Exécution, on obtient ça :

    En d’autres termes, quand la valeur est numérique, les 0 non significatifs sont bien supprimés, mais quand la valeur est une chaîne (entre guillemets ici), les 0 sont conservés. z8 est bien un champ Texte dans la table ?

  23. lourme dit :

    Bonjour

    j’ai fait plusieurs essais de format, rien à faire je perds les 0 devant…

    cdt

  24. Hervé Inisan dit :

    lourme > Génial, content que ça marche. :)

    J’imagine qu’il manquait une des 2 virgules dans le DoCmd, ce qui fait que le filtre était à la mauvaise place (et donc ignoré).

    Pour ce qui est des 0 significatifs : je ne pense pas que le Format(..., "000") soit utile sur le champ z8. La fonction Format() sert à formater une valeur (nombre, date) en texte. Mais si la valeur d’origine est de type Texte, ce n’est pas utile. Je mettrais juste un rst("z8") à cet endroit.

    Mais sinon, ça peut être un effet de bord de ma fonction StringFormat(), il faudra que je pointe ça.

  25. lourme dit :

    Bonjour

    c’est parfait ; j’ai adapté le code pour ne générer l’état qu’à chaue changement de z8….

    dernière question : dans les noms de pdf générés, je n’ai pas les 0 non significatifs
    Exemple Inspection 5196 au lieu de Inspection 05196

    Y a t’il une astuce ?

    Merci d’avance

  26. lourme dit :

    EUREKA !!!

    j’avais une erreur de syntaxe…

    j’ai recodé :
    DoCmd.OpenReport strReportName, acViewPreview, _
    , strWhere, , acHidden

    et ça marche

    Merci pour ton tout

  27. lourme dit :

    Re,

    voici les deux modules que j’ai pour imprimer en pdf

    Sub PrintAsPDF( _
    ByVal strFilename As String, _
    ByVal strReportName As String, _
    Optional ByVal strWhere As String = “”, _
    Optional ByVal blnOpenReader As Boolean = False)

    ‘ Ouvrir l’état en mode caché
    DoCmd.OpenReport strReportName, acViewPreview, _
    strWhere, acHidden

    ‘ Imprimer en PDF
    DoCmd.OutputTo acOutputReport, strReportName, acFormatPDF, _
    strFilename, blnOpenReader

    ‘ Refermer l’état
    DoCmd.Close acReport, strReportName
    End Sub

    et l’autre

    Sub CreerFichesInterlocuteurs()
    Dim strFichier As String
    Dim strFichierPDF As String
    Dim strEtat As String
    Dim strFiltre As String
    Dim rst As DAO.Recordset

    ‘ Nom de l’état à imprimer
    strEtat = “test2″

    ‘ Nom de base du fichier PDF à créer
    ‘ strFichier = DossierSpecial(Bureau) & “Inspection {0} – {1}.pdf”

    strFichier = “K:LilleGGVIEMOA_LILLE1_MOA_GC_BO_MVSMOA_GC_BO_MVS_GANPATProjetsRemu Gan Pat 2013Tableaux de comm” _
    & “Inspection {0} – {1}.pdf”

    ‘ Ouvrir la liste des personnes
    Set rst = CurrentDb.OpenRecordset(“tableau”, dbOpenSnapshot)

    ‘ Parcourir toute la liste
    While Not rst.EOF
    ‘ Le nom du fichier varie en fonction de la personne
    strFichierPDF = StringFormat(strFichier, _
    Format(rst(“z8″), “000″), _
    rst(“nominsp”))

    ‘ Construire le filtre
    ‘ strFiltre = “[z8] = ” & rst(“z8″)

    strFiltre = “[z8] = ‘” & rst(“z8″) & “‘”

    ‘ Imprimer l’état en le filtrant sur la personne concernée
    PrintAsPDF strFichierPDF, strEtat, strFiltre

    ‘ Personne suivante
    rst.MoveNext
    Wend

    ‘ Terminé !
    rst.Close
    Set rst = Nothing
    MsgBox “Opération terminée !”, vbInformation
    End Sub

    y a t’il quelque chose de mal codé ? on dirait que le filtre n’est pas actif ?

    Merci d’avance

    cdt

  28. lourme dit :

    Re

    tout d’abord merci……

    oui cela fonctionne et me génère bien un état avec les enreg du z8 = 1314405

    cdt

  29. Hervé Inisan dit :

    lourme > Le problème est peut-être ailleurs. Sans passer par le générateur de PDF, que fait cette commande :

    (en la tapant dans la fenêtre Exécution).

    Normalement, elle devrait ouvrir l’état manuellement, sur l’enregistrement concerné. Si l’aperçu est incorrect à ce niveau (trop de pages), c’est que le problème est sur l’état. Sinon, c’est dans le code VBA.

  30. lourme dit :

    Bonjour

    ça ne fonctionne toujours pas…. du coup j’ai fait un autre test :
    dans mon fichier en entrée je n’ai gardé qu’un seul enregistrement par inspecteur, j’ai donc pu dans ma table déclarer ma zone z8 comme clé primaire ==> même résultat,access me génère bien des fichiers différents mais avec l’intégralité des données à chaque fois : pas de filtre (ci-dessous les valeurs de ma table)

    z8
    1314405
    1500001
    1540209
    1752406

    que faire ??

    merci d’avance

  31. Hervé Inisan dit :

    lourme > Dans ce cas, la ligne de construction du filtre devrait être :

    Il y a aura autant de pages dans le PDF que de données filtrées sur la valeur de z8.

  32. lourme dit :

    Z8 est déclaré en texte….

    cdt

  33. Hervé Inisan dit :

    lourme > z8 est un champ texte ou numérique ?

  34. lourme dit :

    Re

    j’ai un état qui fait x pages et je voudrais envoyer un pdf à chaque inspecteur (les pages qui lui correspondent)

    la zone inspecteur de ma table s’appelle z8 et j’ai codé cei dans mon module :

    ‘ Parcourir toute la liste
    While Not rst.EOF
    ‘ Le nom du fichier varie en fonction de la personne
    strFichierPDF = StringFormat(strFichier, _
    Format(rst(“z8″), “000″), _
    rst(“nominsp”))

    ‘ Construire le filtre
    ‘ strFiltre = “[z8] = ” & rst(“z8″)

    strFiltre = “[z8] = ” & rst(“z8″)

    ‘ Imprimer l’état en le filtrant sur la personne concernée
    PrintAsPDF strFichierPDF, strEtat, strFiltre

    ‘ Personne suivante
    rst.MoveNext
    Wend

    j’ai bien plusieurs pdf en sortie, mais avec l’intégralité de l’état à chaque fois…

    merci d’avance

    cordialement

  35. lourme dit :

    Re

    en fait j’ai un fichier en entrée qui contient x lignes…

    mon état, génère x pages par inspecteur et mon but est d’envoyer à chaque inspecteur un pdf qui contient toutes ses pages… l’inspecteur étant sur plusieurs lignes je ne peux pas le définir comme clé primaire

    mon filtre actuel est : strFiltre = “[z8] = ‘” & rst(“z8″) & “‘”

    z8 étant le nom de ma zone dans ma table

    merci de votre aide

    cdt

  36. Hervé Inisan dit :

    lourme > A priori, on peut avoir un filtre basé sur un champ quelconque (voire une combinaison de champs).

    L’avantage de la clef primaire est que c’est le seul champ fiable (par définition) pour différencier les enregistrements. En d’autres termes, avec la clef primaire, on est sûr d’avoir des enregistrements séparés ; avec un autre champ, on peut obtenir plusieurs enregistrements sur le même état. Et plus le champ est général, plus on aura de pages.

    Mais c’est peut-être aussi un problème de syntaxe sur le filtre. Quelle est la ligne de filtre actuelle, en VBA ?

  37. lourme dit :

    Re

    j’arrive bien à générer les pdf mais ils contiennent à chaque fois l’intégralité de l’état
    le filtre que j’ai mis en place n’est pas sur la clé primaire, est ce un souci ? peut on avoir un filtre qui n’est pas sur la clé primaire ?

    merci d’avance

    cdt

  38. lourme dit :

    Re…. j’ai trouvé erreur de syntaxe

    merci

  39. lourme dit :

    Bonjour Hervé

    merci beaucoup…. mais j’ai maintenant un autre souci :

    erreur 3464
    Type de données incompatible dans l’expression du critère

    et quand je clique sur Débogage il me surligne les lignes ci-dessous

    DoCmd.OpenReport strReportName, acViewPreview, , _
    strWhere, acHidden

    auriez vous une idée ?

    merci d’avance

  40. Hervé Inisan dit :

    lourme > Est-ce que la bibliothèque DAO est activée dans le projet VBA ? (voir l’article Références pour plus d’infos).

  41. lourme dit :

    bonjour

    j’ai testé cette fonctionnalité (impression dans plusieurs pdf) et j’ai un souci à l’éxécution

    j’ai une erre ur de compilation sur Dim rst As dao.Recordset
    qui me dit Type défini par l’utilisateur non défini

    merci pour votre aide

  42. Hervé Inisan dit :

    DenisS > Bonne pioche… :)

  43. DenisS dit :

    Il y a un exemple dans C:Program FilesPDFCreatorCOMWindows Scripting HostVBScriptsCombineJobs.vbs, aisément transposable en VBA.

    On peut même réordonner les pages avant de combiner :)

  44. Hervé Inisan dit :

    DenisS > Merci Denis pour la confirmation et les pistes (je teste de mon côté dès que possible).

  45. DenisS dit :

    Je confirme, c’est possible.

    Il faut mettre l’imprimante en pause (méthode .cPrinterStop = True), puis imprimer les différents états. La fusion se fait alors à l’aide de la méthode .CombineAll.

    Et finalement, on lance ‘l’impression’ avec .cPrinterStop = False

  46. Hervé Inisan dit :

    Guillaume > A priori, ça doit être possible si on passe par PDFCreator (pas par la fonction PDF native d’Access 2007 et plus). PDFCreator a une fonctionnalité d’assemblage de PDF. Mais je n’ai pas eu l’occasion de vérifier si elle est exploitable en VBA.

  47. Guillaume dit :

    Bonjour,
    Merci pour cet article !
    Je souhaiterais également pouvoir sortir plusieurs formulaires (ou états) en un seul pdf. Cela est-il possible ?
    Cordialement
    Guillaume

  48. Hervé Inisan dit :

    Stephanie > You’re welcome ;)

  49. Stephanie dit :

    YES !!! Génial ça marche !! Bien vu. Merci beaucoup pour votre réactivité et efficacité.
    Bonne journée.
    Stéphanie

  50. Hervé Inisan dit :

    Stephanie > Il manque une virgule avant le strWhere. Du coup, Access cherche une requête au lieu d’appliquer un filtre dynamique. Ceci doit expliquer cela… :)

  51. Stephanie dit :

    Access 2007
    Ca s’arrête ici :
    DoCmd.OpenReport strReportName, acViewPreview, strWhere

  52. Hervé Inisan dit :

    Stephanie > Quand tu cliques sur “Débogage”, le programme s’arrête sur quelle ligne ?

    Et tu as quelle version d’Access ?

  53. Stephanie dit :

    Oui le champ SIRET figure bien dans ma table (clé primaire), et l’état est bien basé sur cette table. Et le champ SIRET est affiché dans l’état.

  54. Hervé Inisan dit :

    Stephanie > Dans le doute : est-ce que le champ SIRET figure bien dans la table/requête qui est source de l’état, et est-ce que ce champ est affiché sur l’état ?

  55. Stephanie dit :

    Bonjour,
    Merci pour vous réponses rapides.
    Malheuresement j’ai toujours le même message d’erreur … alors je ne vois pas d’où ça vient. Je pense que je vais essayer de tout reprendre à zéro, j’ai dû rater quelquechose avant.
    J’ai bien noté la différence d’écriture compte tenu de mon critère qui est en texte.
    Cordialement,
    Stéphanie

  56. Hervé Inisan dit :

    Stephanie > Dans ce cas, le critère doit plutôt s’écrire :

    puisqu’en SQL le critère serait de la forme :

  57. Stephanie dit :

    Oui SIRET écrit comme ça, et de type texte.

  58. Hervé Inisan dit :

    Stephanie > Donc, si j’ai suivi : le champ SIRET existe bien (écrit comme ça) dans la table ouverte lors du OpenRecordset() ?

    Est-ce que ce champ est de type Numérique ou de type Texte ?

  59. Stephanie dit :

    Bonjour,
    Je pense avoir fait toute la procédure comme il faut, mais quand je lance la macro il ne va pas au bout en m’indiquant le message d’erreur suivant : le moteur de base de données n’a pu trouver l’objet “[SIRET]=99999999900011″. Assurez vous que l’objet existe et que vous avez correctement saisi son nom et chemin d’accès. Mon SIRET correspond à votre id (je veux éditer 1 pdf pour chaque SIRET)
    J’ai tapé ça : strFiltre = “[SIRET] = ” & rst(“SIRET”)
    Et bien revérifié les noms de ma table et état.
    Je n’arrive pas à trouver d’où vient mon erreur … avez vous une idée ?
    Merci d’avance, et merci pour votre super site !
    Cordialement,
    Stéphanie

  60. Hervé Inisan dit :

    Célène2002 > La plupart des bouts de code de se tapent dans des modules standard. Tu as un lien dans l’article qui te renvoie vers un autre billet du site qui explique ce que sont les modules standard, et comment les utiliser.

    A noter que cet article repose aussi sur d’autres billets du site, il faut que tu reprennes tous les bouts de code donnés précédemment. Tous les liens figurent plus haut.

  61. Célène2002 dit :

    Je voudrais faire ce qui est expliqué ci-dessus, mais je ne comprend pas où l’on tape la code. Quelqu’un pourrait m’expliquer la procédure. J’ai fait mes tables, ma requête, mon formulaire, mon état. Reste juste à faire ce code pour Imprimer en PDF la fiche de poste de chaque personne de façon distincte. Merci

  62. Hervé Inisan dit :

    liseMels > La fonction DossierSpecial(Programmes) ne renvoie que le dossier C:\Program Files. Il faut lui ajouter le sous-dossier où est installé Access. Ça peut donner quelque chose comme ceci :

    Par contre, ça suppose qu’Access est installé dans le même sous-dossier pour toutes les machines (et qu’il s’agit du même Access, ici la version 14). Si les configurations sont différentes, il faut sans doute une autre approche.

  63. liseMels dit :

    Bonjour,
    J’ai utilisé l’outil ci-haut avec tous les fichiers recommandés et ça fonctionne très bien après avoir ajusté les infos pour mes besoins.
    J’ai, cependant, une question concernant le fonctionnement du fichier “DossierSpecial”. J’aimerais ouvrir une base de données en me servant de ce fichier mais je n’y arrive pas. Voici la ligne de code que j’utilise présentement :
    Shell “””C:Program Files (x86)Microsoft OfficeOffice14MSAcCESS.exe”” “”C:PartageMTLBDProjets.accdb”””
    J’ai essayé plusieurs combinaison comme : strChemin = DossierSpecial(Programmes) & “PartageMTLBDDATABASE.MDB”
    Il faut que je trouve une solution puisque la base de données access est utilisé dans un répertoire partagé et qu’il y a des ordinateurs qui n’ont pas Window 7 mais window XP.

    Merci à l’avance pour votre aide.

  64. Hervé Inisan dit :

    federici > Le principe est le même pour un formulaire. Mais les formulaires ne sont pas destinés à l’impression (donc par extension aux PDF) : ils n’ont pas autant de réglages que les états pour cet usage. Un formulaire imprimé est surtout une copie d’écran brute.

  65. federici dit :

    je souhaiterais faire la meme chose a partir d’un formulaire. Peut-on sortir en format PDF avec snapshot mais a partir de formulaires et non plus d’etats

Laisser un commentaire

Votre adresse de messagerie ne sera pas publiée. Les champs obligatoires sont indiqués avec *

Vous pouvez utiliser ces balises et attributs HTML : <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code class="" title="" data-url=""> <del datetime=""> <em> <i> <q cite=""> <strike> <strong> <pre class="" title="" data-url=""> <span class="" title="" data-url="">