Themabewertung:
  • 0 Bewertung(en) - 0 im Durchschnitt
  • 1
  • 2
  • 3
  • 4
  • 5
Automatisches Erstellen von PDFs - die Lösung
#1
Moin Leon,

bei allem Fairständnis, dass Dein Thema von Steve geschlossen wurde, sollst Du nicht dabei der Leidtragende sein.

Deshalb hier eine einfache VBA-Lösung, deren Einbau in Dein Workbook Schritt für Schritt beschrieben ist. Kein Panik, es ist auch für VBA-Neulinge (also solche die es zu schätzen lernen werden  Wink ) leicht und in wenigen Minuten machbar.

  1. Du öffnest die Arbeitsmappe, aus der die PDFs generiert werden sollen und erstellst mit Speichern unter eine Kopie im Format .xlsb. Die vorherige Version wird nicht mehr gebraucht.
  2. Mit Alt + F11 kommst Du in den VB-Editor. Links oben siehst Du ein Fenster VBA-Projekt mit all Deinen Arbeitsblättern. Falls nicht hilft Strg + R weiter.
  3. Mit einem Rechtsklick in dieses Fenster wird Dir Einfügen angeboten, wo Du Modul wählst.
  4. Durch Doppelklick auf Modul1 öffnet sich rechts das große Fenster für den Code des Moduls. Dort kopierst Du den folgenden Code komplett hinein (ohne die Überschrift Code:) und speicherst Deine Datei

Code:
Option Explicit

Sub Export_To_PDF()
Dim sht As Worksheet, sPath$, sFile$, aSheets(), item
'###### Hier bitte anpassen/ergänzen: Die Namen der Blätter, die Du exportieren möchtest
aSheets = Array("Bericht_A", "Bericht_B")
'###### Hier bitte anpassen: Wo sollen die PDFs abgelegt werden.
'###### So werden sie direkt im Verzeichnis Deines Workbooks abgelegt.
sPath = ThisWorkbook.Path

For Each sht In ThisWorkbook.Sheets
    For Each item In aSheets
        If sht.Name = item Then
'##### Hier bitte anpassen: Der Dateiname wird aus Blattname & Datum zusammengesetzt
            sFile = sPath & "\" & sht.Name & "_" & Date
            sht.ExportAsFixedFormat Type:=xlTypePDF, Filename:=sFile, Quality:=xlQualityStandard
        End If
    Next
Next

End Sub

     5. In Zeile 6 findest Du ein Array (eine Liste) mit Beispielnamen Deiner Arbeitsblätter, die Du bitte anpasst. Achte dabei auf die Syntax: Jeder Blattname muss genau so in
         Anführungszeichen stehen, wie Du ihn unten in der Mappe siehst und vom nächsten durch ein Komma getrennt sein. Wenn Du dynamische Namen hast, zeige mir hier eine Liste 
         aller Blattnamen und ich passe Dir den Code entsprechend an.
     6. Direkt darunter definierst Du das Verzeichnis, in das die PDFs abgelegt werden sollen. Willst Du die Dateien z.B. im Verzeichnis "D:\Meine PDFs" ablegen, ersetzt Du
        ThisWorkbook.Path durch den Verzeichnisnamen in Anführungszeichen.
     7. In Zeile 15 (s. oben im Editor-Menü) wird vor dem Druck der Blatt = Dateiname um das aktuelle Datum ergänzt. Wenn Du das nicht möchtest, setzt Du direkt nach sht.name ein
        Hochkomma (über der Raute).
     8. Nach Deinen Anpassungen speicherst Du die Date erneut

Den letzten Schritt machst Du in DieseArbeitsmappe: Durch Doppelklick öffnest Du deren Codefenster und kopierst diesen Code dort hinein:
Code:
Option Explicit

Private Sub Workbook_Open()
    Application.OnKey "({F12})", "Export_To_PDF"
End Sub

setzt Deinen Cursor hinter Workbook_Open() und drückst F5. Du siehst erst mal kein Ergebnis, aber: Damit wird F12 diesem Makro zugeordnet und Du kannst Deine PDFs mit nur einem Tastendruck exportieren. Willst Du eine andere F-Taste, achte auf Anführungsstriche und Klammern!

Wie kann's noch besser werden? Dass Du jedes Mal auch noch sehen willst, wie die PDFs denn aussehen, wird Dir sicher igendwann lästig werden. Daher habe ich es hier weggelassen - es ist aber natürlich möglich. 

Als interessante Ergänzung könnte ich mir aber vorstellen, dass die Berichte sofort oder später per Outlook verschickt werden und dabei aus demAusgabeordner in den Unterordner Versandt verschoben werden.

Lass wissen, was das veraltete VBA Dir noch Gutes tun kann  Tongue

Schöne Grüße
----------------------------------------------------------------------------------------------------
d'r Bastler von den VBAsteleien.de
Win 10 + Office 2024 & Win11 + Office 2021 + Visio 2019 pro & macOS.X15 + Office2019 pro & Android12 & XL365
Zitieren
#2
Hi,

theoretisch würde in der Hauptroutine auch eine Schleife reichen. Dann braucht man auch kein If.
Code:
Option Explicit

Sub Export_To_PDF()
Dim sPath$, sFile$, aSheets(), item
'###### Hier bitte anpassen/ergänzen: Die Namen der Blätter, die Du exportieren möchtest
aSheets = Array("Bericht_A", "Bericht_B")
'###### Hier bitte anpassen: Wo sollen die PDFs abgelegt werden.
'###### So werden sie direkt im Verzeichnis Deines Workbooks abgelegt.
sPath = ThisWorkbook.Path

For Each item In aSheets
'##### Hier bitte anpassen: Der Dateiname wird aus Blattname & Datum zusammengesetzt
    sFile = sPath & "\" & item & "_" & Date
    Worksheets(item).ExportAsFixedFormat Type:=xlTypePDF, Filename:=sFile, Quality:=xlQualityStandard
Next

End Sub

Vorteil: weniger Overhead
Nachteil: Sollte ein Blattname nicht vorhanden sein, gibt es einen Fehler.
Gruß,
Helmut
_____
Office365 auf MacOS und Win11
Zitieren
#3
Moin Helmut,

na da habe ich Deinen Vorschlag doch mal gleich ausprobiert und festgestellt, dass sich mit Timer kein nennenswerter Unterschied messen lässt: Beide Codes liegen zeitlich quasi gleich auf. Das ist dann eher der Umfang des Inhalt der Sheets der Knackpunkt.

Wenn leon aber zum Beispiel mit Tages- und Wochenberichten arbeitet gibt's den Wochenbericht (weil dynamisch generiert) wohl nur am Freitag und dann würde der Knopfdruck an vier von funf Tagen rausfliegen. Wohl kaum Sinn der Sache ... Wink und nochmal ein Argument für dynamisch erstellte Ausgabe-Formate.

Sicher könnte man in Deinem Code den Wochentag abfangen und dann die Abfrage entsprechend modifizieren. Warum denn einfach, wenns auch kompliziert geht...

Schöne Grüße
----------------------------------------------------------------------------------------------------
d'r Bastler von den VBAsteleien.de
Win 10 + Office 2024 & Win11 + Office 2021 + Visio 2019 pro & macOS.X15 + Office2019 pro & Android12 & XL365
Zitieren
#4
Hi Bastler,

"Overhead" drückt sich, wie du schon selbst bemerkt hast, nicht nur in Millisekunden aus, sondern auch in der Komplexität der Programmierung. Aber du darfst dich gerne auch mit zehn Schleifen und neun If-s austoben, wenn es dir Spaß macht.

Immerhin habe ich den "Nachteil" meiner Methode gleich mit aufgeführt. Und wenn man "fehlende" Blätter ignorieren will, dann kann man das so machen:
Code:
Option Explicit

Sub Export_To_PDF()
Dim sPath$, sFile$, aSheets(), item
'###### Hier bitte anpassen/ergänzen: Die Namen der Blätter, die Du exportieren möchtest
aSheets = Array("Bericht_A", "Bericht_B")
'###### Hier bitte anpassen: Wo sollen die PDFs abgelegt werden.
'###### So werden sie direkt im Verzeichnis Deines Workbooks abgelegt.
sPath = ThisWorkbook.Path

For Each item In aSheets
'##### Hier bitte anpassen: Der Dateiname wird aus Blattname & Datum zusammengesetzt
    sFile = sPath & "\" & item & "_" & Date
    On Error Resume Next
        Worksheets(item).ExportAsFixedFormat Type:=xlTypePDF, Filename:=sFile, Quality:=xlQualityStandard
    On Error Goto 0
Next

End Sub
Gruß,
Helmut
_____
Office365 auf MacOS und Win11
Zitieren
#5
Also - ich sehe in meinem Code aktuell eine Schleife mit zwei Durchläufen und dann eine, deren Durchläufe  durch die Anzahl der Blätter bestimmt wird und diese trifft Dich nicht weniger.
Von zehn Schleifen und neun IFs kann ich da nichts entdecken.

Wenn Du tatsächlich optimieren willst, gibt es da durchaus Potential. Schau mal:
Code:
Option Explicit

Sub Export_To_PDF()
Dim sht As Worksheet, sPath$, sFile$
sPath = ThisWorkbook.Path

For Each sht In ThisWorkbook.Sheets
        Select Case sht.Name
            Case "Bericht_A", "Bericht_B"
            sFile = sPath & "\" & sht.Name & "_" & Date
            sht.ExportAsFixedFormat Type:=xlTypePDF, Filename:=sFile, Quality:=xlQualityStandard
        End Select
Next

End Sub

Da ist's tatsächlich nur noch genau eine Schleife, es braucht kein Array, kein Variant für die items.

Stellt sich die Frage, was soll denn Dein Gemecker?
Schönn Amnd noch ...
Hier noch als Nachtrag die Timer-Zeiten: vHK 0,14453125, v1 0,140625, v2 0,140625. Deine Version vHK ist die langsamste ... knapp 2,8 % langsamer ... immerhin ... Ich hole mir dann mal 'nen Doppelkorn  Big Grin
----------------------------------------------------------------------------------------------------
d'r Bastler von den VBAsteleien.de
Win 10 + Office 2024 & Win11 + Office 2021 + Visio 2019 pro & macOS.X15 + Office2019 pro & Android12 & XL365
Zitieren
#6
(13.04.2026, 17:22)d'r Bastler schrieb: Da ist's tatsächlich nur noch genau eine Schleife, es braucht kein Array, kein Variant für die items.
Eine Schleife über alle vorhandenen Blätter. Bei mir ist es eine Schleife über alle gewünschte Blätter - aber geschenkt, so kann man es auch machen.

(13.04.2026, 17:22)d'r Bastler schrieb:
Stellt sich die Frage, was soll denn Dein Gemecker?
Habe ich irgendwo gemeckert? Wenn du jeden Hinweis auf mögliche Verbesserungen als Gemecker empfindest und dies mit fetter Schrift herausschreist, wo bleibt dann dein freundlicher Umgangston?

Immerhin hast du erkannt, dass eine Schleife ausreicht. Und damit dieser Thread nicht ebenso wie der vorherige gesperrt wird, war das jetzt mein letzter Post dazu.
Gruß,
Helmut
_____
Office365 auf MacOS und Win11
Zitieren
#7
Na - dann Prösterchen Wink !
----------------------------------------------------------------------------------------------------
d'r Bastler von den VBAsteleien.de
Win 10 + Office 2024 & Win11 + Office 2021 + Visio 2019 pro & macOS.X15 + Office2019 pro & Android12 & XL365
Zitieren
#8
Ok Helmut,

dann mal ganz kleingeschrieben, damit Du meine Kommentar nicht wieder als Gebrüll verstehst. Die Frage, was Du mit Deinen Ergänzungen erreichen wolltest hast Du leider nicht beantwortet. Wirklich erkennbare Vorteile konnte ich auch nicht finden. Aber durch Deine Formulierung austoben und unsinnige Behauptungen dazu, habe ich das schon als Gemecker empfunden. 

Ich habe aber Deinen Hinweis durch alle / durch die gewünschten aufgegriffen und das hier gebaut:

Code:
Sub Export_To_PDF_v3()
Dim sht As Worksheet, sPath$, sFile$, aSheets(), item, tStart#

sPath = ThisWorkbook.Path
aSheets = Array("Bericht_A", "Bericht_B")

    tStart = Timer

    For Each item In aSheets
        sFile = sPath & "\" & item & "_" & Date & ".pdf"
        Worksheets(item).ExportAsFixedFormat Type:=xlTypePDF, Filename:=sFile, Quality:=xlQualityStandard
    Next item

    Debug.Print "v3 " & Timer - tStart
End Sub

Auch dieser Code ist Fehler-stabil und tut was er soll. 

Wenn ich jetzt mal für alle Versionen die Timer-Werte vergleiche, stelle ich fest, dass sie 1.) pro Durchlauf variieren und 2.) sich unterm Strich alle so wenig unterscheiden, dass man definitiv von keiner besseren Version sprechen kann. Wir streiten also um des Kaisers Bart. Und den hamwer ja nu schon lange nich mehr.

Was "Eleganz" (= Minialismus) im Coding betrifft, gefällt mir meine Select-Version am besten.

Schönen Amnd noch und Dank für die Anregungen!
----------------------------------------------------------------------------------------------------
d'r Bastler von den VBAsteleien.de
Win 10 + Office 2024 & Win11 + Office 2021 + Visio 2019 pro & macOS.X15 + Office2019 pro & Android12 & XL365
Zitieren


Gehe zu:


Benutzer, die gerade dieses Thema anschauen: 1 Gast/Gäste




Hinweis auf Angebot Excel-Inside - lang    Keine Lösung gefunden? Du kannst Dich gerne an unser erfahrenes Experten-Team wenden um dein Anliegen zu besprechen.
   Gerne erstellen wir auf dieser Basis ein Angebot.
   Sende deine Anfrage einfach
per E-Mail an anfrage@excel-inside.de


Powerd and supported by Excel-InsideSolutions