IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

PyQt Python Discussion :

QPrinter et html


Sujet :

PyQt Python

  1. #1
    Membre à l'essai
    Homme Profil pro
    Enseignant
    Inscrit en
    Septembre 2017
    Messages
    30
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Calvados (Basse Normandie)

    Informations professionnelles :
    Activité : Enseignant
    Secteur : Enseignement

    Informations forums :
    Inscription : Septembre 2017
    Messages : 30
    Points : 17
    Points
    17
    Par défaut QPrinter et html
    Bonjour,

    Dans l'application que je développe le fichier html généré est converti en pdf par l'intermédiaire de wkhtmltopdf. Je voudrais (si j'y arrive) le faire avec QPrinter. Le souci est que le fichier pdf généré par QPrinter n'est pas du tout bon, c'est très certainement lié à la qualité du fichier html.

    Pouvez-vous m'aider ?

    Je vous mets le code de QPrinter par lequel je passe (pour l'instant je fais des tests) :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    #!/usr/bin/python
    #-*- coding: utf-8 -*-
     
    import sys
    from PyQt4.QtCore import *
    from PyQt4.QtGui import *
     
    class Html_vers_pdf(QPrinter):
        def __init__(self, fichier):
            super(Html_vers_pdf, self).__init__(QPrinter.HighResolution)
     
            html_file_path = open(fichier).read()
     
            html_file_path = html_file_path.decode('utf-8')
     
            self.doc = QTextDocument()
     
            self.doc.setHtml(html_file_path)
            self.printer = QPrinter(QPrinter.HighResolution)
            self.printer.setOutputFormat(QPrinter.PdfFormat)
            self.printer.setOrientation(QPrinter.Portrait)
            self.printer.setPaperSize(QPrinter.A4)
     
            self.printer.setPageMargins(10, 10, 10, 10, QPrinter.Millimeter)
            print u"Le fichier pdf a été crée !"
            self.printer.setOutputFileName("essaiPDF.pdf")
     
            self.doc.print_(self.printer)
     
    if __name__ == '__main__':
    	app = QApplication(sys.argv)
    	Html_vers_pdf('3eme_collages_et_diverses_associations_sequence_1_POUR_L_ELEVE.html')
    Je vous mets aussi le fichier html (qui avec wkhtmltopdf me donne quelque chose de bien (ce que je veux obtenir en fait) :

    3eme_collages_et_diverses_associations_sequence_1_POUR_L_ELEVE.html

    Le fichier pdf généré dans mon application par wkhtmltopdf :

    3eme_collages_et_diverses_associations_sequence_1_POUR_L_ELEVE.pdf

    Voilà le fichier pdf généré avec QPrinter avec mes essais :

    essaiPDF.pdf

    Si quelqu'un ici pouvait regarder le fichier html et me dire ce qui coince pour que QPrinter puisse faire le boulot correctement, ce serait super ...

    Merci d'avance.

    Bonne journée.

  2. #2
    Expert éminent
    Avatar de tyrtamos
    Homme Profil pro
    Retraité
    Inscrit en
    Décembre 2007
    Messages
    4 462
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2007
    Messages : 4 462
    Points : 9 249
    Points
    9 249
    Billets dans le blog
    6
    Par défaut
    Bonjour,

    En fait, Qt ne comprend pas le html complet, mais seulement un sous-ensemble appelé "richtext". C'est un peu dommage, parce que ça ne permet pas d'utiliser directement un script construit avec un éditeur html sans modification à la main. Cependant, avec un peu de pratique, je confirme qu'on peut construire à peu près n'importe quel pdf avec Qt! Y compris avec en-têtes et bas-de-pages.

    Voir le sous-ensemble "richtext": http://doc.qt.io/qt-5/richtext-html-subset.html.
    Un expert est une personne qui a fait toutes les erreurs qui peuvent être faites, dans un domaine étroit... (Niels Bohr)
    Mes recettes python: http://www.jpvweb.com

  3. #3
    Membre à l'essai
    Homme Profil pro
    Enseignant
    Inscrit en
    Septembre 2017
    Messages
    30
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Calvados (Basse Normandie)

    Informations professionnelles :
    Activité : Enseignant
    Secteur : Enseignement

    Informations forums :
    Inscription : Septembre 2017
    Messages : 30
    Points : 17
    Points
    17
    Par défaut
    Citation Envoyé par tyrtamos Voir le message
    Bonjour,

    En fait, Qt ne comprend pas le html complet, mais seulement un sous-ensemble appelé "richtext". C'est un peu dommage, parce que ça ne permet pas d'utiliser directement un script construit avec un éditeur html sans modification à la main. Cependant, avec un peu de pratique, je confirme qu'on peut construire à peu près n'importe quel pdf avec Qt! Y compris avec en-têtes et bas-de-pages.

    Voir le sous-ensemble "richtext": http://doc.qt.io/qt-5/richtext-html-subset.html.
    tyrtamos merci pour ta réponse. Je vais essayer de réecrire le code html généré par mon application (mais ça va pas être facile !).
    Je pense que c'est aussi les tableaux (et les cellules) qui posent un souci, puisque aucune bordure de tableau n'apparaît dans le pdf généré par QPrinter.
    Est-ce que quelqu'un ici a un retour d'expérience sur l'écriture des entêtes html qui fonctionne bien avec QPrinter ? (un exemple à montrer), de même pour un tableau (balises table, td, tr, ... comment bien gérer ça).

    Bonne fin de soirée.

  4. #4
    Membre à l'essai
    Homme Profil pro
    Enseignant
    Inscrit en
    Septembre 2017
    Messages
    30
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Calvados (Basse Normandie)

    Informations professionnelles :
    Activité : Enseignant
    Secteur : Enseignement

    Informations forums :
    Inscription : Septembre 2017
    Messages : 30
    Points : 17
    Points
    17
    Par défaut
    Bonjour,

    Voilà j'ai réussi à avoir quelque chose d'assez sympathique en utilisant QPrinter, voilà mon code (qu'il faut que je mette en place dans mon application) :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
    156
    157
    158
    159
    160
    161
    162
    163
    164
    165
    166
    167
    168
    169
    170
    171
    172
    173
    174
    175
    176
    177
    178
    179
    180
    181
    182
    183
    184
    185
    186
    187
    188
    189
    190
    191
    192
    193
    194
    195
    196
    197
    198
    199
    200
    201
    202
    203
    204
    205
    206
    207
    208
    209
    210
    211
    212
    213
    214
    215
    216
    217
    218
    219
    220
    221
    222
    223
    #!/usr/bin/python
    #-*- coding: utf-8 -*-
     
    from __future__ import division
     
    import sys, os
    from PyQt4.QtCore import *
    from PyQt4.QtGui import *
    #from PyQt4.QtWebKit import *
     
    class Html_vers_pdf_fiche_eleve(QPrinter):
        def __init__(self, niv_de_classe, nbre_seances, titre_prog, num_seq, incitation, demande, vocabulaire, questions, texte_ref_art_1, texte_ref_art_2, texte_ref_art_3, vignette_img_src_1, vignette_img_src_2, vignette_img_src_3, liste_comp_et_pts_chiffres, marge_gauche, marge_droite, marge_haute, marge_basse, police_normaux_caracteres, police_petits_caracteres):
            super(Html_vers_pdf_fiche_eleve, self).__init__(QPrinter.HighResolution)
     
            # Rubriques ...
            variable_001 = "Classe :"
            variable_002 = "Date :"
            variable_003 = "Durée :"
            variable_004 = "Nom :"
            variable_005 = "Prénom :"
            variable_006 = "Titre de la progression :"
            variable_007 = "Séquence n° :"
            variable_008 = "Incitation :"
            variable_009 = "Demande :"
            variable_010 = "Vocabulaire :"
            variable_011 = "Questions (répondre derrière cette feuille) EVENTUELLEMENT ECRIRE UN COMMENTAIRE :"
            variable_012 = ''
            variable_014 = "Travaux d'artistes (références) :"
            variable_015 = "Les élèves, évaluez vontre travail en utilisant les smileys juste en dessous de Eval Elève"
            variable_016 = "Eval Elève"
            variable_017 = "Evaluation Professeur"
            variable_018 = "Ci-dessous se trouvent les critères d'évaluation des compétences travaillées en arts plastiques"
     
            # HTML ; écriture de l'entête
            html_entete = '''<html><head><title></title>'''+'''\n'''+'''<style type="text/css">'''+'''\n'''+'''table { border-style:solid;border-width:1.2px;border-color:#6e6e6e;font-size:'''+str(police_normaux_caracteres)+'''pt;font-family: "DejaVu Sans, sans-serif" }'''+'''\n'''+'''</style>'''+'''\n'''+'''</head>'''+'''\n'''+'''<body>'''+'''\n'''
            html_entete = html_entete.decode('utf-8')
     
            # HTML ; écriture du niveau de classe, de la date et de la durée
            html_tab_ligne_0 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="22%"><p><b>'''+str(variable_001)+''' '''+str(niv_de_classe)+'''ème</b></p></td>'''+'''\n'''+'''<td width="35%"><p><b>'''+str(variable_002)+'''</b></p></td>'''+'''\n'''+'''<td width="43%"><p><b>'''+str(variable_003)+''' '''+nbre_seances+'''</b></p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_0 = html_tab_ligne_0.decode('utf-8')
     
            # HTML ; écriture du nom et du prénom
            html_tab_ligne_1 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="50%"><p><b>'''+str(variable_004)+'''</b></p></td>'''+'''\n'''+'''<td width="50%"><p><b>'''+str(variable_005)+'''</b></p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_1 = html_tab_ligne_1.decode('utf-8')
     
            # HTML ; écriture du titre de la progression et du numéro de la séquence
            html_tab_ligne_2 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.6">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="83%"><p><b><u>'''+str(variable_006)+'''</u>'''+''' '''+titre_prog+'''</b></p></td>'''+'''\n'''+'''<td width="17%"><p><u><b>'''+str(variable_007)+'''</u>'''+''' <b>'''+str(num_seq)+'''</b></p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_2 = html_tab_ligne_2.decode('utf-8')
     
            # HTML ; écriture de l'incitation
            html_tab_ligne_3 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="100%" bgcolor="#e1dede"><p><b><u>'''+str(variable_008)+'''</u>'''+''' '''+incitation+'''</b></p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_3 = html_tab_ligne_3.decode('utf-8')
     
            # HTML ; écriture de la demande
            html_tab_ligne_4 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.6">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="100%" bgcolor="#e1dede"><p><b><u>'''+str(variable_009)+'''</u></b>'''+''' '''+demande+'''</p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_4 = html_tab_ligne_4.decode('utf-8')
     
            # HTML ; écriture de l'entête de la liste des mots de vocabulaire
            html_tab_ligne_5 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5" bgcolor="#cccccc">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="100%"><p><b><u>'''+str(variable_010)+'''</u></b></p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_5 = html_tab_ligne_5.decode('utf-8')
     
            # HTML ; écriture de la liste des mots de vocabulaire
            html_tab_ligne_6 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="100%"><p>'''+vocabulaire+'''</p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_6 = html_tab_ligne_6.decode('utf-8')
     
            # HTML ; écriture de l'entête des questions posées aux élèves
            html_tab_ligne_7 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5" bgcolor="#cccccc">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="100%"><p><u><b>'''+str(variable_011)+'''</b></u></p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_7 = html_tab_ligne_7.decode('utf-8')
     
            # HTML ; écriture des questions posées aux élèves
            html_tab_ligne_8 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="100%"><p><b>'''+questions+'''</b></p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_8 = html_tab_ligne_8.decode('utf-8')
     
            # HTML ; écriture de l'entête Travaux d'artistes (références)
            html_tab_ligne_9 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5" bgcolor="#cccccc">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="100%"><p><u><b>'''+str(variable_014)+'''</b></u></p></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_9 = html_tab_ligne_9.decode('utf-8')
     
            # HTML ; écriture du nom de l'artiste, de l'oeuvre, d'un résumé et des vignettes correspondantes
            html_tab_ligne_10 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="33%"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><b>'''+texte_ref_art_1+'''</b></font><br />'''+'''<div align="center">'''+vignette_img_src_1+'''</div><p />'''+'''</td>'''+'''\n'''+'''<td width="33%"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><b>'''+texte_ref_art_2+'''</b></font><br />'''+'''<div align="center">'''+vignette_img_src_2+'''</div><p />'''+'''</td>'''+'''\n'''+'''<td width="34%"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><b>'''+texte_ref_art_3+'''</b></font><br />'''+'''<div align="center">'''+vignette_img_src_3+'''</div><p />'''+'''</td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_10 = html_tab_ligne_10.decode('utf-8')
     
            # HTML ; écriture de l'entête de l'évaluation
            # élève et de l'évaluation professeur
            html_tab_ligne_11 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="69.8%" bgcolor="#696969"><font color="#E5E4E2" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b>'''+str(variable_015)+'''</b></p></font></td>'''+'''\n'''+'''<td width="11.2%" bgcolor="#acabab"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt"><p><b>'''+str(variable_016)+'''</b></p></font></td>'''+'''\n'''+'''<td width="19%" bgcolor="#696969"><font color="#E5E4E2" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b>'''+str(variable_017)+'''</b></p></font></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_11 = html_tab_ligne_11.decode('utf-8')
     
            # HTML ; écriture de l'entête de l'évaluation des compétences 
            # travaillées en arts plastiques + les points chiffrés associés
            html_tab_ligne_12 = '''<table width="100%" cellpadding="3"
                    cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="70.2%" bgcolor="#979290"><font color="#ffffff" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b>'''+str(variable_018)+'''</b></p></font></td>'''+'''\n'''+'''<td width="3%">'''+'''\n'''+'''<img src="'''+os.getcwd()+'''/smileys_evaluation/smiley_pas_content_orange_18x18.png" width="18" height="18">'''+'''\n'''+'''<td width="3%">'''+'''\n'''+'''<img src="'''+os.getcwd()+'''/smileys_evaluation/smiley_neutre_jaune_18x18.png" width="18" height="18">'''+'''\n'''+'''<td width="3%">'''+'''\n'''+'''<img src="'''+os.getcwd()+'''/smileys_evaluation/smiley_content_vert_18x18.png" width="18" height="18">'''+'''\n'''+'''</td>'''+'''\n'''+'''<td width="2%" bgcolor="#ff9900"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b>I</b></p></font></td>'''+'''\n'''+'''<td width="2%" bgcolor="#ffff00"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt"><p><b>F</b></p></font></td>'''+'''\n'''+'''<td width="2%" bgcolor="#99ff33"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b>S</b></p></font></td>'''+'''\n'''+'''<td width="2%" bgcolor="#66ff00"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b>TB</b></p></font></td>'''+'''\n'''+'''<td width="11%" bgcolor="#99ffcc"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b>Pts Chiffrés</b></p></font></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n'''
            html_tab_ligne_12 = html_tab_ligne_12.decode('utf-8')
     
            # HTML ; écriture des critères d'évaluation
            # -----------------------------------------
            # Liste des critères d'évaluation
            html_tab_ligne_13 = []
            # Boucle qui remplit la liste des critères d'évaluation
            for comp_pts in enumerate(liste_comp_et_pts_chiffres) :
                competence = liste_comp_et_pts_chiffres[comp_pts[0]][0]
                points = liste_comp_et_pts_chiffres[comp_pts[0]][1]
                html_tab_ligne_13.append('''<table width="100%" cellpadding="3"
                cellspacing="0.5">'''+'''\n'''+'''<tr>'''+'''\n'''+'''<td width="70.2%" bgcolor="#ffffff"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b>'''+competence+'''</b></p></font></td>'''+'''\n'''+'''<td width="3.73%">'''+'''\n'''+''' '''+'''\n'''+'''<td width="3.73%">'''+'''\n'''+''' '''+'''\n'''+'''<td width="3.66%">'''+'''\n'''+''' '''+'''\n'''+'''</td>'''+'''\n'''+'''<td width="1.95%" bgcolor="#ff9900"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b> </b></p></font></td>'''+'''\n'''+'''<td width="2%" bgcolor="#ffff00"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt"><p><b> </b></p></font></td>'''+'''\n'''+'''<td width="2.1%" bgcolor="#99ff33"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b> </b></p></font></td>'''+'''\n'''+'''<td width="2.6%" bgcolor="#66ff00"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b> </b></p></font></td>'''+'''\n'''+'''<td width="11%" bgcolor="#99ffcc"><font color="#000000" size="'''+str(police_petits_caracteres)+'''pt" family="DejaVu Sans, sans-serif"><p><b><div align="right"> /'''+points+'''</div></b></p></font></td>'''+'''\n'''+'''</tr>'''+'''\n'''+'''</table>'''+'''\n''')
            html_tab_ligne_13 = ''.join(html_tab_ligne_13).decode('utf-8')
     
            # # HTML ; écriture de la fin de la page
            html_body_html_final = '''</body></html>'''
            html_body_html_final = html_body_html_final.decode('utf-8')
     
            #
            self.doc = QTextDocument()
     
            # Ecriture de la syntaxe HTML finale
            self.doc.setHtml(html_entete + html_tab_ligne_0 + html_tab_ligne_1 + html_tab_ligne_2 + html_tab_ligne_3 + html_tab_ligne_4 + html_tab_ligne_5 + html_tab_ligne_6 + html_tab_ligne_7 + html_tab_ligne_8 + html_tab_ligne_9 + html_tab_ligne_10 + html_tab_ligne_11 + html_tab_ligne_12 + html_tab_ligne_13 + html_body_html_final)
     
            # Ecriture du fichier PDF par QPrinter
            self.printer = QPrinter(QPrinter.HighResolution)
            self.printer.setOutputFormat(QPrinter.PdfFormat)
            self.printer.setOrientation(QPrinter.Portrait)
            self.printer.setPaperSize(QPrinter.A4)
            # La taille des marges est convertie en millimètres
            self.printer.setPageMargins(int(marge_gauche*10), int(marge_droite*10), int(marge_haute*10), int(marge_basse*10), QPrinter.Millimeter)
            #self.printer.setResolution(72)
     
            print u"Le fichier pdf a été crée !"
            self.printer.setOutputFileName("essaiPDF.pdf")
     
            """
            ###################### ESSAI pied de page ... je ne comprend pas tout !
            print 'self.printer.resolution()', self.printer.resolution()
            mm = 25.4 * self.printer.resolution()
            print 'mm', mm
            
            # ---------------------------------------
            # --> https://pl.python.org/forum/index.php?action=profile;u=1626;sa=showPosts;start=75
            innerRect = self.printer.pageRect() ################
            innerRect.setBottom(innerRect.bottom() - 300) ##############
            contentRect = QRectF(0, 0, self.printer.width(), self.doc.size().height()) ##########
            currentRect = QRectF(0, 0, innerRect.width(), innerRect.height()) ################
            self.doc.setTextWidth(currentRect.width() - 20) ###################
            print "self.doc.size().height()", self.doc.size().height() ############
            print "currentRect.width()", currentRect.width() #############
            print "currentRect", currentRect ###############
            # -----------------------------------------
            
            self.painter = QPainter()
            
            #self.painter = QPainter(self.printer)
            #self.painter.save()
            self.painter.begin(self.printer)
            # configurer la police de caractères
            self.painter.setFont(QFont("DejaVu Sans, sans-serif", 12))
            self.painter.setPen(QColor(0, 0, 0))
            
            # rectangle d'impression du texte (coordonnées du papier)
            self.rect = self.printer.pageRect()
            print "self.rect", self.rect
            # mettre pour le doc le même rectangle d'impression que printer
            self.doc.setPageSize(QSizeF(QSize(self.rect.size().width(), self.rect.size().height())))
            
            dimension_page = self.printer.paperSize(QPrinter.Millimeter)
            hauteur = dimension_page.height()
            largeur = dimension_page.width()
            print "Dimension de la page : ", str(hauteur)+"x"+str(largeur)
            
            #
            texte_pied_de_page = '''"'''+titre_prog[7:-7]+'''"    ['''+str(niv_de_classe)+'ème]  '+'''  '''+'SEQ '+str(num_seq)
            
            self.painter.drawText(QRectF(0, 0, 9000, 13500), Qt.AlignCenter|Qt.AlignBottom, texte_pied_de_page.decode('utf-8'))
            #self.painter.drawText(currentRect, Qt.AlignCenter|Qt.AlignBottom, texte_pied_de_page.decode('utf-8'))
            #self.painter.drawText(self.rect_b, QtCore.Qt.AlignVCenter | QtCore.Qt.AlignHCenter, "Bas de page")
     
            #self.painter.save()
            self.painter.end()
            ###################### ESSAI pied de page ... je ne comprend pas tout !
            """
     
            self.doc.print_(self.printer)
     
    if __name__ == '__main__':
        app = QApplication(sys.argv)
        #############################################
        # Juste pour l'exemple ici, assignation des données
        #
        # (Réglages) Valeurs des marges
        marge_gauche = 0.90 # marge en cm
        marge_droite = 0.90 # marge en cm 
        marge_haute = 0.90 # marge en cm 
        marge_basse = 0.90 # marge en cm
        #
        # (Réglages) Taille de la police
        # ------------------------------------------
        # Texte partie générale (taille de la police)
        taille_police_texte_general = 9
        # Texte travaux d'artistes et évaluation (taille de la police)
        taille_police_trav_artist_et_eval = 7
        #
        liste_vocab = ['<b><u>Mot de vocabulaire 1 :</u></b> La définition du mot de vocabulaire 1 ... '+'bla bla blablablabla '*10+'<br />', '<b><u>Mot de vocabulaire 2 :</u></b> La définition du mot de vocabulaire 2.<br />', '<b><u>Mot de vocabulaire 3 :</u></b> La définition du mot de vocabulaire 3 ...'+'bla bla blablablabla '*14+'<br />', '<b><u>Mot de vocabulaire 4 :</u></b> La définition du mot de vocabulaire 4 ...'+'bla bla blablablabla '*17+'<br />', '<b><u>Mot de vocabulaire 5 :</u></b> La définition du mot de vocabulaire 5.<br />', '<b><u>Mot de vocabulaire 6 :</u></b> La définition du mot de vocabulaire 6.<br />', '<b><u>Mot de vocabulaire 7 :</u></b> La définition du mot de vocabulaire 7 ...'+'bla bla blablablabla '*5+'<br />', '<b><u>Mot de vocabulaire 8 :</u></b> La définition du mot de vocabulaire 8.']
        #
        liste_questions = ["1) Est-ce que QPrinter est intéressant ?, ... oui en fait.<br />", "2) Est-ce que c'est facile à manipuler ?, ... oui quand on a compris comment ça fonctionne.<br />", "3) Est-ce que QPrinter est pratique ?, ... oui oui !, dans mon cas pour faire quelque chose en full Python, sans devoir appeler (et embarquer) un programme tiers."]
        #
        liste_textes_art = ['''* Tom Wesselmann, "Still Life 20" (1962). Résumé du contexte de l'oeuvre ... '''+"bla bla blablablabla "*16, '''* Georges Meliès, "Le voyage dans la lune" (1902). Résumé du contexte de l'oeuvre ...'''+"bla bla blablablabla "*18, '''* Louise Nevelson, "Sky cathedral" (1958) ... bois peint en noir ...'''+"bla bla blablablabla "*10]
        #
        liste_img_src_ref_art = ['''<img src="'''+os.getcwd()+'''/z_img_essai_pour_qprinter/tom_wesselmann_still_life_20_vue_01.jpg"'''+''' width="200" height="196" />''', '''<img src="'''+os.getcwd()+'''/z_img_essai_pour_qprinter/georges_melies_le_voyage_ds_la_lune_1902.png"'''+''' width="200" height="150" />''', '''<img src="'''+os.getcwd()+'''/z_img_essai_pour_qprinter/louise_nevelson_sky_cathedral_bois_peint_en_noir_1958.png"'''+''' width="200" height="159" />''']
        #
        liste_criteres_eval = ["Critère d'évaluation 1"+" Blabla bla"*10, "Critère d'évaluation 2"+" Blabla bla"*8, "Critère d'évaluation 3"+" Blabla bla"*5]
        liste_points_chiffres = ['8', '4', '8']
        #
        liste_pts_et_comp = zip(liste_criteres_eval, liste_points_chiffres)
        #############################################
        # Appel de la classe
        Html_vers_pdf_fiche_eleve(3, "2 à 3 séances", "&quot; Une progression avec un titre &quot;", 1, "&quot; Une incitation qui n'en dit pas trop ! &quot;", "La demande est faite pour faire en sorte que l'élève comprenne un peu plus ce qu'il y a à faire mais en même temps cette demande ne lui donne pas trop de pistes de travail afin que la situation problème (énoncée par l'incitation) soit tout de même présente."+" Blabla blablabla "+"blablabla blabla"*32, ''.join(liste_vocab), ''.join(liste_questions), liste_textes_art[0], liste_textes_art[1], liste_textes_art[2], liste_img_src_ref_art[0], liste_img_src_ref_art[1], liste_img_src_ref_art[2], liste_pts_et_comp, marge_gauche, marge_droite, marge_haute, marge_basse, taille_police_texte_general, taille_police_trav_artist_et_eval)
    Voilà ce que j'obtiens avec une séquence d'élève bidon :

    essaiPDF.pdf

    Le résultat est pas mauvais du tout. Je suis content de pouvoir utiliser QPrinter pour faire le boulot car je vais ma passer de devoir embarquer wkhtmltopdf, c'est une très bonne chose.

    Un souci malgré tout ; je n'arrive pas à changer la taille de la petite police, taille_police_trav_artist_et_eval et police_petits_caracteres dans le code (certainement que je m'y prends mal avec le code html à ce niveau).

    D'autre part j'aimerais aussi mettre en place un pied de page, ... mais là je n'y arrive pas du tout !!! . tyrtamos si tu as un peu de temps à m'accorder, peux-tu m'expliquer ?, ... j'ai vu ce sujet (message n°2), mais j'avoue que je ne comprend pas le fonctionnement.

    Merci d'avance.

    A bientot.

  5. #5
    Expert éminent
    Avatar de tyrtamos
    Homme Profil pro
    Retraité
    Inscrit en
    Décembre 2007
    Messages
    4 462
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2007
    Messages : 4 462
    Points : 9 249
    Points
    9 249
    Billets dans le blog
    6
    Par défaut
    Bonjour,

    Citation Envoyé par ekdmekdm Voir le message
    tyrtamos si tu as un peu de temps à m'accorder, peux-tu m'expliquer ?
    Ok mais je suis très pris en ce moment, et il faut que je me remette ça en tête: c'est assez complexe. Laisse moi quelques jours.
    Un expert est une personne qui a fait toutes les erreurs qui peuvent être faites, dans un domaine étroit... (Niels Bohr)
    Mes recettes python: http://www.jpvweb.com

  6. #6
    Expert éminent
    Avatar de tyrtamos
    Homme Profil pro
    Retraité
    Inscrit en
    Décembre 2007
    Messages
    4 462
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Var (Provence Alpes Côte d'Azur)

    Informations professionnelles :
    Activité : Retraité

    Informations forums :
    Inscription : Décembre 2007
    Messages : 4 462
    Points : 9 249
    Points
    9 249
    Billets dans le blog
    6
    Par défaut
    Bonjour,

    Voilà, j'ai fini par préparer quelque chose qui pourrait convenir. Désolé pour le délai de réponse!

    Il s'agit donc de fabriquer avec PyQt des pdf multipages avec possibilité d'entêtes et de bas de pages.

    Voilà les quelques principes que j'ai retenus:

    - on prépare ce qu'il faut intégrer sous forme de 3 fichiers écrits en "richtext" (le html de Qt): corpsdetexte.html, entete.html et basdepage.html. Si on veut intégrer des données qui changent à chaque session (date, nom du fichier, nom du destinataire, etc...) voire à chaque page (numéro de page), on utilise la méthode "format" appliquée aux chaines html.

    - si on ne veut pas d'entête, il suffit de ne pas réserver de place pour ça (enteteHT=0). Idem pour le bas de page (basdepageHT=0).

    - J'ai mis à titre d'option un entourage des zones d'écriture avec des rectangles à coins arrondis: il suffit de mettre les quelques lignes en commentaire pour s'en passer.

    - pour faciliter la mise en page, toutes les données numériques sont en mm. Elles seront converties en pixels dans le programme en fonction de la résolution du printer.

    - le code est présenté sous forme d'une bibliothèque Python à importer. Je l'ai appelé "bibpdfeb.py" ("eb" pour entête et bas de page). Je donne aussi un code test ("test.py") qui donne un exemple d'appel de la bibliothèque.

    - Pour écrire l'entête et le bas de page, j'ai choisi d'utiliser la méthode "drawStaticText" du painter, qui a l'énorme avantage de supporter le richtext contrairement à "drawText". A la place, on peut aussi utiliser "drawText", "drawImage" (,etc...) mais il faut écrire du code Python spécifique à chaque fois. Dans tous les cas, il faut recalculer les coordonnées x et y en pixels du coin gauche-haut à partir du coin similaire du corps du texte qui est x=0 et y=0 dans chaque page. Cela donne un "y" négatif pour l'entête, mais les fonctions Qt acceptent sans problème. On peut même avec ça (je l'ai déjà fait) écrire une adresse postale à l'emplacement de la fenêtre d'une enveloppe à fenêtre: dans ce cas, l'entête écrit dans l'emplacement du corps du texte!!! Cela me permet tous les ans d'envoyer à 500 personnes dans le monde entier (40 pays) des courriers email personnalisés avec pdf en pièce jointe (résultats d'un concours international de photos).

    Voilà le code de la bibliothèque "bibpdfeb.py". Le code est largement commenté:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
    156
    157
    158
    159
    160
    161
    162
    163
    164
    165
    166
    167
    168
    169
    170
    171
    172
    173
    174
    175
    176
    177
    178
    179
    180
    181
    182
    183
    184
    185
    186
    187
    188
    189
    190
    191
    192
    193
    194
    195
    196
    197
    198
    199
    200
    201
    202
    203
    204
    205
    206
    207
    208
    209
    210
    211
    212
    213
    214
    215
    216
    217
    218
    219
    220
    221
    222
    223
    224
    225
    226
    227
    228
    229
    230
    231
    232
    233
    234
    235
    236
    237
    238
    239
    240
    241
    242
    243
    244
    245
    246
    247
    248
    249
    250
    251
    252
    253
    254
    255
    256
    257
    258
    259
    260
    #!/usr/bin/python
    # -*- coding: utf-8 -*-
    # Python 3 et Qt 5
     
    import os
    import time
     
    from PyQt5 import (QtCore, QtGui, QtPrintSupport)
     
    #############################################################################
    def affiche_url(url):
        """affiche le contenu d'un fichier sur disque ou sur réseau ou d'une
           adresse internet avec le programme par défaut de l'OS
        """
        url = url.strip()
        if len(url) != 0:
            if url.startswith("~"):
                # expansion adresse fichier du home utilisateur
                url = os.path.expanduser(url)
            if os.path.exists(url):
                if url[:2] in [r"\\", "//"]:
                    # adresse fichier sur réseau
                    qurl = QtCore.QUrl(url, QtCore.QUrl.TolerantMode)
                else:
                    # adresse fichier sur disque local
                    url = os.path.abspath(url)  # => calcul adresse absolue
                    qurl = QtCore.QUrl().fromLocalFile(url)
            else:
                # adresse internet
                qurl = QtCore.QUrl().fromUserInput(url)
            if not qurl.isValid():
                return False  # url invalide: on ne fait rien!
     
            # appelle le programme par défaut de l'OS pour affichage de l'url
            ouvrefichier = QtGui.QDesktopServices()
            ok = ouvrefichier.openUrl(qurl)
     
            return ok
     
    #############################################################################
    def datedujour():
        """Donne la date du jour sous le format 'jj/mm/aaaa' pour affichage
         (ex: '13/07/2012')
         """
        return time.strftime('%d/%m/%Y')
     
    #############################################################################
    class ImprimeEB(object):
     
        #========================================================================
        def __init__(self, fichierpdf="", corpsdetexte="", margeGT=20, margeHT=10,
                           margeDT=10, margeBT=10, entete="", enteteHT=0,
                           basdepage="", basdepageHT=0, sepHT=2):
     
            # NB: toutes les données numériques des arguments sont en mm
     
            # fichier pdf à créer
            self.fichierpdf = fichierpdf  
     
            # corps du document en html (richtext de Qt)
            self.doc = QtGui.QTextDocument()
            self.doc.setHtml(corpsdetexte)  # charge le texte
     
            self.margeGT = margeGT  # marge Gauche Totale en mm
            self.margeHT = margeHT  # marge Haute Totale en mm
            self.margeDT = margeDT  # marge Droite Totale en mm
            self.margeBT = margeBT  # marge Basse Totale en mm
     
            # document d'entête en html (richtext de Qt)
            self.entete = entete
            self.enteteHT = enteteHT  # hauteur totale réservée pour l'entête en mm
     
            # document de bas de page en html (richtext de Qt)
            self.basdepage = basdepage
            self.basdepageHT = basdepageHT  # hauteur totale réservée pour le bas de page en mm
     
            # hauteur de séparation en mm entre entete, corps de texte et bas de page
            self.sepHT = sepHT
     
            # format de l'imprimante pdf par défaut
            self.formatpapier = QtPrintSupport.QPrinter.A4
            self.orientation = QtPrintSupport.QPrinter.Portrait  # ou QtPrintSupport.QPrinter.Landscape
     
            # concerne l'option des encadrements à coins arrondis
            self.rayon = 2 # rayon des coins arrondis en mm
            self.margint = 1 # marge intérieure G et D en mm
     
            #--------------------------------------------------------------------
            # initialise les variables d'instance définies plus loin
            self.printer = None
            self.mm2px = None
            self.contentRect = None
            self.currentRect = None
            self.rect_t = None
            self.nbpages = None
            self.rect = None
            self.painter = None
     
        # =======================================================================
        def imprimeEntete(self, numpage=0):
            """Imprime l'entête de la page numpage
            """
     
            # crée un QStaticText qui contient le texte html de l'entête
            qtexte = QtGui.QStaticText(self.entete)
            qtexte.setTextFormat(QtCore.Qt.RichText) # force l'usage du html
     
            # définit le rectangle d'écriture de l'entête
            largeurtexte = self.mm2px(self.printer.widthMM())
            qtexte.setTextWidth(largeurtexte)
            x = 0
            y = 0 - self.mm2px(self.sepHT + self.enteteHT)
     
            # sauve les valeurs du painter
            self.painter.save()
     
            # met un QFont par défaut pour ajuster la taille des fontes à la résolution du printer
            self.painter.setFont(QtGui.QFont("Helvetica", 10))
     
            # écrit le texte d'entete html 
            self.painter.drawStaticText(x, y, qtexte)
     
            # option: dessine un entourage avec coins arrondis autour de l'entête
            rect_e = QtCore.QRect(x-self.mm2px(self.margint), y, self.mm2px(self.printer.widthMM()+2*self.margint), self.mm2px(self.enteteHT))
            rayon = float(self.mm2px(self.rayon))
            self.painter.drawRoundedRect(rect_e, rayon, rayon)
     
            # restaure les valeurs du painter
            self.painter.restore()
     
        # =======================================================================
        def imprimeBasdepage(self, numpage=0):
            """Imprime le bas de page de la page numpage
            """
     
            # crée un QStaticText qui contient le texte html du basdepage
            qtexte = QtGui.QStaticText(self.basdepage)
            qtexte.setTextFormat(QtCore.Qt.RichText) # force l'usage du html
     
            # définit le rectangle d'écriture du bas de page
            largeurtexte = self.mm2px(self.printer.widthMM())
            qtexte.setTextWidth(largeurtexte)
            x = 0
            y = 0 + self.mm2px(self.printer.heightMM() + self.sepHT)
     
            # sauve les valeurs du painter
            self.painter.save()
     
            # met un QFont par défaut pour ajuster la taille des fontes à la résolution du printer
            self.painter.setFont(QtGui.QFont("Helvetica", 10))
     
            # écrit le texte du bas de page html 
            self.painter.drawStaticText(x, y, qtexte)
     
            # option: dessine un entourage avec coins arrondis autour du bas de page
            rect_b = QtCore.QRect(x-self.mm2px(self.margint), y, self.mm2px(self.printer.widthMM()+2*self.margint), self.mm2px(self.basdepageHT))
            rayon = float(self.mm2px(self.rayon))
            self.painter.drawRoundedRect(rect_b, rayon, rayon)
     
            # restaure les valeurs du painter
            self.painter.restore()
     
     
        # =======================================================================
        def imprime(self):
     
            # crée et configure l'imprimante printer
            self.printer = QtPrintSupport.QPrinter(QtPrintSupport.QPrinter.HighResolution)
            self.printer.setPaperSize(self.formatpapier)
            self.printer.setOrientation(self.orientation)
            self.printer.setOutputFormat(QtPrintSupport.QPrinter.PdfFormat)
            self.printer.setOutputFileName(self.fichierpdf)
     
            # fonction pour convertir des mm en pixels en fonction de la résolution du printer
            self.mm2px = lambda mm: int(mm * self.printer.resolution() / 25.4)
     
            # mettre une fonte par défaut pour ajuster la taille des fontes du doc à la résolution du printer
            font = QtGui.QFont("Helvetica", 10)
            paintFont = QtGui.QFont(font, self.printer)
            self.doc.setDefaultFont(paintFont)
     
            # hauteur en pixels à réserver pour l'en-tête
            enteteH = self.mm2px(self.enteteHT)
            # hauteur en pixels à réserver pour le bas de page
            basdepageH = self.mm2px(self.basdepageHT)
     
            # hauteur en pixels de la séparation entre entete, corps de texte et bas de page 
            separation = self.mm2px(self.sepHT)
     
            # marges en pixels pour définir le rectangle d'impression de chaque page
            margeG = self.mm2px(self.margeGT)
            margeH = self.mm2px(self.margeHT)
            if enteteH != 0:
                margeH += separation + enteteH
            margeD = self.mm2px(self.margeDT)
            margeB = self.mm2px(self.margeBT)
            if basdepageH != 0:
                margeB += separation + basdepageH
     
            # initialisation du rectangle d'impression du texte avec les marges
            self.printer.setPageMargins(margeG, margeH, margeD, margeB, QtPrintSupport.QPrinter.DevicePixel)
     
            # rectangle d'impression du texte (coordonnées du papier)
            self.rect = self.printer.pageRect()
            # mettre pour le doc le même rectangle d'impression que printer
            self.doc.setPageSize(QtCore.QSizeF(QtCore.QSize(self.rect.size().width(), self.rect.size().height())))
     
            # rectangle d'impression du texte ((0,0) => coord. pt haut et gauche)
            self.rect_t = QtCore.QRect(0, 0, self.rect.size().width(), self.rect.size().height())
     
            # grand rectangle d'impression de tout le doc
            self.contentRect = QtCore.QRectF(QtCore.QRect(QtCore.QPoint(0, 0), self.doc.size().toSize()))
            # rectangle d'impression courant de la page
            self.currentRect = QtCore.QRectF(QtCore.QRect(QtCore.QPoint(0, 0), self.rect.size()))
     
            # crée le painter lié au printer
            self.painter = QtGui.QPainter(self.printer)
     
            # sauvegarde les valeurs du painter
            self.painter.save()
     
            # nombre total de pages du doc à imprimer
            self.nbpages = self.doc.pageCount()
     
            # impression de toutes les pages
            for numpage in range(1, self.nbpages + 1):
     
                # imprime le corps du texte sur la page courante
                self.doc.drawContents(self.painter, QtCore.QRectF(self.currentRect))
                self.currentRect.translate(0, self.currentRect.height())
                self.painter.restore()
     
                # imprime l'en-tête si c'est demandé
                if enteteH != 0:
                    self.imprimeEntete(numpage)
     
                # imprime le bas de page si c'est demandé
                if basdepageH != 0:
                    self.imprimeBasdepage(numpage)
     
                # option: dessine un entourage avec coins arrondis autour du corps de texte
                rect_t = QtCore.QRect(0-self.mm2px(self.margint), 0, self.mm2px(self.printer.widthMM()+2*self.margint), self.mm2px(self.printer.heightMM()))
                rayon = self.mm2px(self.rayon)
                self.painter.drawRoundedRect(rect_t, rayon, rayon)
     
                # sauvegarde le painter
                self.painter.save()
     
                # décale la partie à imprimer de la hauteur de la zone d'impression
                self.painter.translate(0, -self.currentRect.height() * numpage)
     
                # provoque un changement de page s'il reste quelque chose à imprimer
                if self.currentRect.intersects(self.contentRect):
                    self.printer.newPage()
     
            # restaure le painter
            self.painter.restore()
     
            # fin d'impression
            self.painter.end()
    Voilà le code de test "test.py":

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    #!/usr/bin/python
    # -*- coding: utf-8 -*-
    # Python 3, PyQt5
     
     
    import sys
    import os
     
    from bibpdfeb import ImprimeEB, affiche_url
     
    from PyQt5 import QtCore, QtWidgets
     
     
    #############################################################################
    if __name__ == "__main__":
     
        # initialise la bibliothèque graphique
        app = QtWidgets.QApplication(sys.argv)
     
        fichierpdf="exemple.pdf"
     
        # corps de texte
        fichiertexte = "corpsdetexte.html"
        corpsdetexte = ""
        with open(fichiertexte, 'r') as fs:
            for ligne in fs:
                corpsdetexte += ligne.rstrip() + '\r\n'
     
        # marges en mm        
        margeGT=30
        margeHT=10
        margeDT=10
        margeBT=10
     
        # entête
        fichierentete = "entete.html"
        entete=""
        with open(fichierentete, 'r') as fs:
            for ligne in fs:
                entete += ligne.rstrip() + '\r\n'
        # hauteur réservée pour l'entête en mm       
        enteteHT=20
     
        # bas de page
        fichierbasdepage = "basdepage.html"
        basdepage=""
        with open(fichierbasdepage, 'r') as fs:
            for ligne in fs:
                basdepage += ligne.rstrip() + '\r\n'
        # hauteur réservée pour le bas de page en mm        
        basdepageHT=20
     
        # séparateur
        sepHT=2
     
        # appelle l'impression en pdf
        imprime = ImprimeEB(fichierpdf, corpsdetexte, margeGT, margeHT,
                           margeDT, margeBT, entete, enteteHT,
                           basdepage, basdepageHT, sepHT)
     
        # exécute l'impression en pdf
        imprime.imprime()
     
        # affiche le fichier pdf s'il existe
        if os.path.exists(fichierpdf):
            affiche_url(fichierpdf)
    A titre d'exemple un peu "rustique", voilà les 3 fichiers html que j'ai utilisés:
    corpsdetexte.html
    entete.html
    basdepage.html

    Et voilà ce que l'exécution de "test.py" donne comme résultat:

    exemple.pdf

    Ce qui reste à faire:

    - Trouver comment utiliser le "richtext". Pour info, il semble que le script soit un peu ancien: cela veut dire que si un paramètre CSS ne marche pas, il faut essayer l'ancienne solution du paramètre HTML. Je peux cependant témoigner qu'on peut faire de beaux textes: choix de la fonte avec taille et embellissement (gras, italique, sousligné), intégration d'images, tableaux, listes indentées, etc... Mais il faut tâtonner un peu...

    - je ne l'ai pas fait, mais il est possible d'avoir des entêtes et bas de pages différentes en fonction de la page. Mais si la place à réserver est différente, il faudra en tenir compte dans le calcul de la place réservée au corps du texte.

    Tu peux poser des questions! En tout cas, j'espère que ce coup de pousse te servira. Si j'arrive à avoir un peu de temps dans les prochains mois, je ferai un tuto sur mon site web.

    [edit] A noter que les liens hypertextes faisant partie du "richtext" de Qt, on peut mettre de tels liens dans les pages pdf! A titre d'exemple, intégrer cette ligne entre 2 paragraphes dans le fichier html:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    <a href="https://www.google.fr" target="_blank">lien hypertexte</a><br>
    Le fichier étant affiché par le pdfreader d'Adobe, un clic sur ce lien (après accord) affichera la page de google dans le navigateur par défaut de l'OS. On peut aussi mettre un lien qui pointe sur un autre emplacement de la page pdf.
    Un expert est une personne qui a fait toutes les erreurs qui peuvent être faites, dans un domaine étroit... (Niels Bohr)
    Mes recettes python: http://www.jpvweb.com

  7. #7
    Membre à l'essai
    Homme Profil pro
    Enseignant
    Inscrit en
    Septembre 2017
    Messages
    30
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 58
    Localisation : France, Calvados (Basse Normandie)

    Informations professionnelles :
    Activité : Enseignant
    Secteur : Enseignement

    Informations forums :
    Inscription : Septembre 2017
    Messages : 30
    Points : 17
    Points
    17
    Par défaut
    Je répond avec un peu de retard, désolé.

    Je regarde tout ça dès que je peux.

    Merci !

    A bientot.

Discussions similaires

  1. Algorithme de conversion de RTF vers HTML
    Par youtch dans le forum Algorithmes et structures de données
    Réponses: 10
    Dernier message: 10/09/2002, 12h35
  2. Balises HTML dans un fichier XML
    Par Bastet79 dans le forum XML/XSL et SOAP
    Réponses: 12
    Dernier message: 04/09/2002, 15h29
  3. composant builder4 pour afficher du code html
    Par BranRuz dans le forum C++Builder
    Réponses: 2
    Dernier message: 04/09/2002, 11h35
  4. delphi XML / HTML caractéres speciaux !
    Par adem dans le forum EDI
    Réponses: 2
    Dernier message: 29/08/2002, 17h48
  5. [XSLT] inclure du XSL dans une balise html
    Par iaa dans le forum XSL/XSLT/XPATH
    Réponses: 2
    Dernier message: 05/08/2002, 15h57

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo