Spaß mit PDF Erzeugung

Diese Seite verwendet Cookies. Durch die Nutzung unserer Seite erklären Sie sich damit einverstanden, dass wir Cookies setzen. Weitere Informationen

  • Spaß mit PDF Erzeugung

    Hallo,

    für ein Projekt muss ich derzeit ein paar PDF Dateien erzeugen. Da das selber "malen" sehr aufwendig ist war ich über folgendes Tutorial sehr erfreut: github.com/appcoda/Print2PDF

    Hier erstellt man einfach eine HTML-Seite und aus dieser wird mittels verschiedener Apple Methoden eine PDF erzeugt. Funktioniert auch echt klasse bis auf ein Problem.

    Wenn eine Pdf über mehrere Seiten geht tritt das Phänomen, wie im Bild zu sehen, auf. Ich habe bereits alles versucht. Dem gesagt, dass er den Page-Break innerhalb eines TR vermeiden soll, extra ein neues DIV eingeführt und da noch mal gesagt, dass da explizit kein PageBreak sein soll aber immer ohne Erfolg. Was kann ich noch machen? Ich bin am verzweifeln

    Mein Ziel ist es, dass der Text auch auf die neue Seite kommt. Direkt neben das Bild.

    Hier mein Code:

    HTML-Quellcode: main.html

    1. <!DOCTYPE html>
    2. <html>
    3. <head>
    4. <meta content="text/html; charset=utf-8" http-equiv="content-type">
    5. <title>PDF</title>
    6. <style type="text/css">
    7. .report-box,
    8. .imageTable {
    9. max-width:800px;
    10. margin:auto;
    11. padding:30px;
    12. /*border:1px solid #eee;*/
    13. /*box-shadow:0 0 10px rgba(0, 0, 0, .15); */
    14. font-size:16px;
    15. line-height:24px;
    16. font-family:'Helvetica Neue', 'Helvetica', Helvetica, Arial, sans-serif;
    17. color:#555;
    18. }
    19. .report-box table{
    20. width:100%;
    21. line-height:inherit;
    22. text-align:left;
    23. }
    24. .report-box table td,
    25. .imageTable table td {
    26. padding:5px;
    27. vertical-align:top;
    28. }
    29. .report-box table tr td:nth-child(2){
    30. text-align:right;
    31. }
    32. .report-box table tr.top table td{
    33. padding-bottom:20px;
    34. }
    35. .report-box table tr.top table td.title{
    36. font-size:45px;
    37. line-height:45px;
    38. color:#333;
    39. }
    40. .report-box table tr.information table td{
    41. padding-bottom:40px;
    42. }
    43. .report-box table tr.heading td,
    44. .imageTable table tr.heading td{
    45. background:#eee;
    46. border-bottom:1px solid #ddd;
    47. font-weight:bold;
    48. }
    49. .report-box table tr.details td{
    50. padding-bottom:20px;
    51. }
    52. .imageTable table tr.item td{
    53. border-bottom:1px solid #eee;
    54. }
    55. .imageTable table tr.item.last td{
    56. border-bottom:none;
    57. }
    58. .imageTable table, .imageTable tr, .imageTable td, .imageTable th {
    59. page-break-inside: avoid;
    60. }
    61. .imageTable tr.item {
    62. page-break-before: auto;
    63. }
    64. @media only screen and (max-width: 600px) {
    65. .report-box table tr.top table td{
    66. width:100%;
    67. display:block;
    68. text-align:center;
    69. }
    70. .report-box table tr.information table td{
    71. width:100%;
    72. display:block;
    73. text-align:center;
    74. }
    75. }
    76. </style>
    77. </head>
    78. <body>
    79. <div class="report-box">
    80. <table cellpadding="0" cellspacing="0">
    81. <tbody>
    82. <tr class="top">
    83. <td colspan="2">
    84. <table>
    85. <tbody>
    86. <tr>
    87. <td class="title"> <img src="#LOGO_IMAGE#" style="width:100%; max-width:200px; background-color: #cdcdcd">
    88. </td>
    89. <td> <b>PDF zu_</b> #PDF_NUMBER#<br>
    90. #PDF_DATE#</td>
    91. </tr>
    92. </tbody>
    93. </table>
    94. </td>
    95. </tr>
    96. <tr class="information">
    97. <td colspan="2">
    98. <table>
    99. <tbody>
    100. <tr>
    101. <td> #SENDER_INFO# </td>
    102. <td> #RECIPIENT_INFO# </td>
    103. </tr>
    104. </tbody>
    105. </table>
    106. </td>
    107. </tr>
    108. <tr class="heading">
    109. <td> #HEADING# </td>
    110. <td> <br>
    111. </td>
    112. </tr>
    113. <tr class="details">
    114. <td>Mitarbeiter: #EMPLOYEES# </td>
    115. <td> <br>
    116. </td>
    117. </tr>
    118. </table>
    119. </div>
    120. <div class="imageTable">
    121. <table cellpadding="0" cellspacing="0">
    122. <tr class="heading">
    123. <td style="width:50%"> Bild </td>
    124. <td> Beschreibung </td>
    125. </tr>
    126. #ITEMS#
    127. </tbody>
    128. </table>
    129. </div>
    130. </body>
    131. </html>
    Alles anzeigen

    Quellcode: single_item.html

    1. <tr class="item">
    2. <td style="width:50%;"><img src="#IMAGE#" style="margin:0; padding:0; width:100%; display:block;"></td>
    3. <td ">#ITEM_DESC#</td>
    4. </tr>



    Quellcode: last_item.html

    1. <tr class="item last">
    2. <td style="width:50%"><img src="#IMAGE#" style="margin:0; padding:0; width:100%; display:block;"></td>
    3. <td>#ITEM_DESC#</td>
    4. </tr>


    Viele Grüße und Danke
    Nils
    Bilder
    • Bildschirmfoto 2019-01-19 um 09.10.33.png

      552,3 kB, 2.108×818, 43 mal angesehen
  • Mac & i Test Abo
  • Ich habe mir jetzt nicht das ganze Tutorial durchgelesen, aber grundsätzlich dürftest Du ein Problem haben, HTML-seitig Seitenwechsel zu erzwingen. Das ist - nach meinem Verständnis - einfach nicht der Ansatz einer Beschreibungssprache, die eigentlich (!) kein explizites Layout vorgeben will, sondern nur die "Intention" einer Formatierung festlegt (Zitat, Überschrift, ...). Klar, dass dies höhere Ansprüche an Webseiten-Design mittlerweile aufgeweicht haben, aber eine Druckbeschreibungssprache ist HTML definitv nicht.

    Du wirst m. E. nicht umhinkommen, bei der PDF-Erstellung code-seitig die Verteilung auf mehrere Seiten vorzunehmen, indem Du z. B. jeweils ein PDF für eine Seite auslieferst. Tricky ist wahrscheinlich, ohne Kenntnis über das Rendering zu wissen, wie viel auf eine Seite passt. Vielleicht kommt da der Punkt, an dem Du die Ausgabe doch lieber selber zeichnest.

    Mattes
    Diese Seite bleibt aus technischen Gründen unbedruckt.
  • Danke für deine Antwort! Denkst du, dass ich das auch nicht mit Hilfe von CSS machen kann? Also ich habe. ja einige CSS Styles. Und da gibt es Page-Break Befehle. Nur irgendwie setzte ich die ja ein bisschen falsch um.

    Selber Zeichnen wäre halt worst case. Alles bis auf das klappt ja. Und so kann man auch relativ einfach eine Preview umsetzten. Vlt. gibts ja noch andere Ideen.

    Viele grüße
    Nils
  • Meine HTML-Kenntnisse sind schon etwas staubig, aber ich bin recht sicher, dass Du hier konzeptionell an Grenzen stösst: Der HTML-Renderer kannt ja gar nicht die physikalischen Gegebenheiten Deines Druckers.

    Hinzu kommt, dass der UIPageRenderer selbst - durchaus noch bei Anzeigen der Druckvorschau - die Seitengrössen variiert: Erkennbar an Aktualisierungen der Anzeige und auch irgendwo (mein Gedächtnis!) dokumentiert...

    Ich lass mich aber gerne eines Besseren belehren :)

    Mattes

    Edit: Ups, die eigentliche Frage übersehen: CSS retten Dich bestimmt nicht, sie dienen ja letztlich nur der zentralen Definition von Layouteigenschaften, ohne den eigentlichen Funktionsumfang von HTML zu erweitern.
    Diese Seite bleibt aus technischen Gründen unbedruckt.
  • Das Problem ist der Support von den benutzten CSS-Selektoren, wie page-break-inside.
    Eigentlich bietet nur Chrome hier eine halbwegs vernünftige Unterstützung, Safari mag die nicht, gleichwohl die in der neuen CSS3 Spec ohnehin ersetzt werden.

    Eine einfache Lösung wäre es, deinen tr-Tags eine Anzeige als inline-block zu spendieren, so sollte nichts mehr umgebrochen werden.

    Kleiner Vorschlag:

    CSS-Quellcode

    1. .imageTable tr.item{
    2. display: inline-block;
    3. vertical-align: top;
    4. width: 100%;
    5. }
    macht aus dem:


    das hier:


    Gruß

    Dieser Beitrag wurde bereits 1 mal editiert, zuletzt von Spotlight ()

  • Danke dir für den Tipp. Der Umbruch funktioniert jetzt. Nur leider werden die Bilder viel zu klein.

    Vorher gingen die Bilder über 50% der Breite und waren entsprechend hoch. Jetzt sind die Bilder wesentlich kleiner. Kann man das fixen irgendwie? (siehe Bild)

    Viele grüße und Danke
    Nils
    Bilder
    • Bildschirmfoto 2019-01-19 um 16.17.24.png

      175,6 kB, 1.222×352, 35 mal angesehen
  • Die Bilder skalieren jetzt auf ihre angegebene Größe. Am einfachsten und saubersten ist es, statt der Tabelle z. B. einzelne CSS Grids, o. ä. zu nehmen und nen inline-Block drum herum zu legen.
    So behält du alle Freiheiten was das spätere Layouting angeht.

    Mal kurz nachgebaut:

    HTML:

    HTML-Quellcode: HTML

    1. <div class="no-break">
    2. <div class="container">
    3. <div class="content-img">
    4. <img style="width: 100%" src="https://via.placeholder.com/150">
    5. </div>
    6. <div class="content-txt">
    7. 150x150 img
    8. </div>
    9. </div>
    10. </div>

    CSS:


    CSS-Quellcode: CSS

    1. .no-break{
    2. display: inline-block;
    3. width: 100%
    4. }
    5. .container{
    6. display: grid;
    7. grid-template-columns:50% 50%;
    8. margin-bottom: 5px;
    9. }

    Oder vollständig:


    codepen.io/anon/pen/oJKweO



    Gruß