- ベストアンサー
Microsoft Print to PDF
Windows11、エクセル2019です。 エクセルシートをActivesheet.ExportAsFixedFormat Type:=xlTypePDFでPDFに変換するのではなく、Wimdows10以降に内蔵の仮想プリンター、Microsoft Print to PDFでPDFを作成したいのです。理由は細かい表の罫線を正しく表示したいからです。 以下でテストしてみて大丈夫だとは思うのですが、このVBAを記述したエクセルを使う人が大勢いるので、なかにはMicrosoft Print to PDFがプリンター設定にない方もいるのではと懸念します。 もしMicrosoft Print to PDFがプリンター設定にない方がこのコードを動かそうとしたら何か注意メッセージをだそうと思いますが、Microsoft Print to PDFの有無をPrintOutの前に取得する方法はないでしょうか? Private Sub testPDF02() Dim Sh As Worksheet Set Sh = ActiveSheet Dim orgPrinter As String orgPrinter = Application.ActivePrinter Debug.Print "印刷前のプリンタ:" & Application.ActivePrinter Call Sh.PrintOut(ActivePrinter:="Microsoft Print to PDF") Debug.Print "印刷直後のプリンタ:" & Application.ActivePrinter Application.ActivePrinter = orgPrinter Debug.Print "プリンタをもとに戻した:" & Application.ActivePrinter End Sub
- みんなの回答 (2)
- 専門家の回答
質問者が選んだベストアンサー
> Set oQrySet = oWMI.ExecQuery("SELECT * FROM Win32_Printer") > このあたりが全然わかりません。 簡単になんとなくでしか説明できないのですが.ConnectServerでアクセスしたOSの情報の中でプリンターの情報を選択した結果をoQrySetに入れるという感じだと思います。 Query(クエリ)は複数のデータから必要なデータを取得したいときに使う機能で、SELECTのところはSQL文でアクセスとかのDBで使われたりしますしエクセルVBAでも利用することがあります。 このあたりは定型文だと思って利用していいのではと思います。 現状でも問題は無いと思いますが ただ個人的に GoTo は使いたくないのと どちらかというとgetPrinterInfo()はサブだと思いますので メインをtestPDF02()にしてそこから getPrinterInfo()を呼び出す感じにするとどうでしょうか。 この状態にしておくとgetPrinterInfoは他のプロシージャからも利用できます。 (十分なテストをしていないので何か変なことがあるかもしれません) Private Sub testPDF02() Dim Sh As Worksheet Set Sh = ActiveSheet Dim orgPrinter As String If getPrinterInfo("Microsoft Print to PDF") = True Then MsgBox "Microsoft Print to PDF でPDF化します。", vbInformation orgPrinter = Application.ActivePrinter ' Debug.Print "印刷前のプリンタ:" & Application.ActivePrinter Call Sh.PrintOut(ActivePrinter:="Microsoft Print to PDF") ' Debug.Print "印刷直後のプリンタ:" & Application.ActivePrinter Application.ActivePrinter = orgPrinter ' Debug.Print "プリンタをもとに戻した:" & Application.ActivePrinter Else MsgBox "Microsoft Print to PDFが利用できません", vbCritical End If End Sub Function getPrinterInfo(ByVal prtName As String) As Boolean 'SWbemLocatorオブジェクトを作成してWMIに接続 Dim oWMI As Object Set oWMI = CreateObject("WbemScripting.SWbemLocator").ConnectServer 'オブジェクト取得のクエリを実行 Dim oQrySet As Object Set oQrySet = oWMI.ExecQuery("SELECT * FROM Win32_Printer") 'プリンタ情報の取得 Dim oPrint As Object Dim flg As Boolean: flg = False For Each oPrint In oQrySet If oPrint.Name = prtName Then flg = True Exit For End If Next Set oPrint = Nothing Set oQrySet = Nothing Set oWMI = Nothing getPrinterInfo = flg End Function
その他の回答 (1)
- kkkkkm
- ベストアンサー率66% (1742/2617)
On Error GoTo prnErr Application.ActivePrinter = "Microsoft Print to PDF on Ne01:" On Error GoTo 0 Exit Sub prnErr: MsgBox "Microsoft Print to PDFが利用できません", vbCritical というのもありかと思ったのですが「on Ne01」が一定とも限らない気がしますので プリンターの情報を取得する。 https://calmdays.net/vbatips/printerinfo/ 上記のサイトのコードで PCのプリンタ名一覧を取得しながら Microsoft Print to PDFがあればその時点でループを抜けてコードを続行、なければメッセージを出して終了するという方法はいかがでしょう。
お礼
ありがとうございます。 ご教示のサイトの記述を参考に以下のようにしてみましたがこれで正しいでしょうか? Set oQrySet = oWMI.ExecQuery("SELECT * FROM Win32_Printer") このあたりが全然わかりません。 Sub getPrinterInfo() 'SWbemLocatorオブジェクトを作成してWMIに接続 Dim oWMI As Object Set oWMI = CreateObject("WbemScripting.SWbemLocator").ConnectServer 'オブジェクト取得のクエリを実行 Dim oQrySet As Object Set oQrySet = oWMI.ExecQuery("SELECT * FROM Win32_Printer") 'プリンタ情報の取得 Dim oPrint As Object For Each oPrint In oQrySet If oPrint.Name = "Microsoft Print to PDF" Then MsgBox "Microsoft Print to PDF でPDF化します。", vbInformation 'PDF作成呼び出し Call testPDF02 GoTo line End If Next MsgBox "Microsoft Print to PDFが利用できません", vbCritical line: Set oPrint = Nothing Set oQrySet = Nothing Set oWMI = Nothing End Sub Private Sub testPDF02() Dim Sh As Worksheet Set Sh = ActiveSheet Dim orgPrinter As String orgPrinter = Application.ActivePrinter ' Debug.Print "印刷前のプリンタ:" & Application.ActivePrinter Call Sh.PrintOut(ActivePrinter:="Microsoft Print to PDF") ' Debug.Print "印刷直後のプリンタ:" & Application.ActivePrinter Application.ActivePrinter = orgPrinter ' Debug.Print "プリンタをもとに戻した:" & Application.ActivePrinter End Sub
お礼