簡體   English   中英

使用 Adob​​e Acrobat 靜默打印 PDF

[英]Printing a PDF Silently with Adobe Acrobat

嘗試使用 adobe acrobat 在 C# 中以靜默方式打印 pdf 時遇到 2 個問題。 我正在使用 Process.Start() 打印 pdf。

第一個問題是,如果不指定可執行文件的完整路徑,我將無法啟動 Adob​​e Acrobat。 我假設在您安裝它時它不會將它添加到您的路徑中。 有沒有一種簡單的方法可以在不指定完整路徑名的情況下在機器上啟動最新版本的 acrobat? 我擔心客戶端會進行更新並破壞我啟動它的代碼。 我還擔心他們在具有不同 Windows 版本的機器上安裝它(64 位環境與 32 位環境中的安裝路徑不同)。

我的第二個問題是,每當我啟動 acrobat 並打印它時,acrobat 窗口仍然打開。 我認為我使用的命令行參數會抑制所有這些,但顯然不是。

我正在嘗試使用以下語法從命令行啟動 adobe acrobat:

C:\\Program Files (x86)\\Adobe\\Reader 10.0\\Reader>AcroRd32.exe /t "Label.pdf" "HP4000" "HP LaserJet 4100 Series PCL6" "out.pdf"

它打印出來很好,但它仍然使 acrobat 窗口保持打開狀態。 除了出去以編程方式殺死進程之外,還有其他解決方案嗎?

我最終放棄了 Adob​​e Acrobat 並使用FoxIt Reader (免費 pdf 閱讀器)來打印 pdf。 這是我用來在 C# 中通過 FoxIt 打印的代碼:

Process pdfProcess = new Process();
pdfProcess.StartInfo.FileName = @"C:\Program Files (x86)\Foxit Software\Foxit Reader\Foxit Reader.exe";
pdfProcess.StartInfo.Arguments = string.Format(@"-p {0}", fileNameToSave);
pdfProcess.Start();

上面的代碼打印到默認打印機,但您可以使用命令行參數來指定文件和打印機。 您可以使用以下語法:

Foxit Reader.exe -t "pdf 文件名" "打印機名稱"

更新:

顯然,早期版本的 acrobat 也不存在上述問題。 如果您使用更舊的版本(4.x 或類似版本),則不會出現此問題。

一些打印機也支持原生 pdf 打印,因此可以將原始 pdf 數據發送到打印機,它可能會打印出來。 有關將原始數據發送到打印機的信息,請參閱https://support.microsoft.com/en-us/kb/322091

更新 2

在我們軟件的更高版本中,我們最終使用了付費產品:

http://www.pdfprinting.net/

尼克的回答對我來說很好,所以我把它翻譯成 c#。 它有效!

using System.Diagnostics;

namespace Whatever
{
static class pdfPrint
{
    public static void pdfTest(string pdfFileName)
    {
       string processFilename = Microsoft.Win32.Registry.LocalMachine
            .OpenSubKey("Software")
            .OpenSubKey("Microsoft")
            .OpenSubKey("Windows")
            .OpenSubKey("CurrentVersion")
            .OpenSubKey("App Paths")
            .OpenSubKey("AcroRd32.exe")
            .GetValue(String.Empty).ToString();

        ProcessStartInfo info = new ProcessStartInfo();
        info.Verb = "print";
        info.FileName = processFilename;
        info.Arguments = String.Format("/p /h {0}", pdfFileName);
        info.CreateNoWindow = true;
        info.WindowStyle = ProcessWindowStyle.Hidden; 
        //(It won't be hidden anyway... thanks Adobe!)
        info.UseShellExecute = false;

        Process p = Process.Start(info);
        p.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;

        int counter = 0;
        while (!p.HasExited)
        {
            System.Threading.Thread.Sleep(1000);
            counter += 1;
            if (counter == 5) break;
        }
        if (!p.HasExited)
        {
            p.CloseMainWindow();
            p.Kill();
        }
    }
}

}

我試過 Adob​​e Reader 和 Foxit 都沒有運氣。 兩者的當前版本都非常喜歡彈出窗口並讓進程運行。 最終使用了非常不引人注目的蘇門答臘PDF 這是我使用的代碼。 完成打印后,沒有任何窗口和進程退出的痕跡。

    public static void SumatraPrint(string pdfFile, string printer)
    {
        var exePath = Registry.LocalMachine.OpenSubKey(
            @"SOFTWARE\Microsoft\Windows\CurrentVersion" +
            @"\App Paths\SumatraPDF.exe").GetValue("").ToString();

        var args = $"-print-to \"{printer}\" {pdfFile}";

        var process = Process.Start(exePath, args);
        process.WaitForExit();
    }

以下分別在 Acrobat Reader 8.1.3 和 Acrobat Pro 11.0.06 中進行了測試,並確認了以下功能:

  1. 找到系統上的默認 Acrobat 可執行文件
  2. 將文件發送到本地打印機
  3. 關閉 Acrobat,無論版本如何

string applicationPath;

var printApplicationRegistryPaths = new[]
{
    @"SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\Acrobat.exe",
    @"SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\AcroRD32.exe"
};

foreach (var printApplicationRegistryPath in printApplicationRegistryPaths)
{
    using (var regKeyAppRoot = Registry.LocalMachine.OpenSubKey(printApplicationRegistryPath))
    {
        if (regKeyAppRoot == null)
        {
            continue;
        }

        applicationPath = (string)regKeyAppRoot.GetValue(null); 

        if (!string.IsNullOrEmpty(applicationPath))
        {
            return applicationPath;
        }
    }
}

// Print to Acrobat
const string flagNoSplashScreen = "/s";
const string flagOpenMinimized = "/h";

var flagPrintFileToPrinter = string.Format("/t \"{0}\" \"{1}\"", printFileName, printerName); 

var args = string.Format("{0} {1} {2}", flagNoSplashScreen, flagOpenMinimized, flagPrintFileToPrinter);

var startInfo = new ProcessStartInfo
{
    FileName = printApplicationPath, 
    Arguments = args, 
    CreateNoWindow = true, 
    ErrorDialog = false, 
    UseShellExecute = false, 
    WindowStyle = ProcessWindowStyle.Hidden
};

var process = Process.Start(startInfo);

// Close Acrobat regardless of version
if (process != null)
{
    process.WaitForInputIdle();
    process.CloseMainWindow();
}

得到了另一個解決方案……它結合了來自 stackOverflow 的其他片段。 當我調用 CloseMainWindow,然后調用 Kill .. adobe 關閉

    Dim info As New ProcessStartInfo()
    info.Verb = "print"
    info.FileName = Microsoft.Win32.Registry.LocalMachine.OpenSubKey("Software").OpenSubKey("Microsoft").OpenSubKey("Windows").OpenSubKey("CurrentVersion").OpenSubKey("App Paths").OpenSubKey("AcroRd32.exe").GetValue(String.Empty).ToString()
    info.Arguments = String.Format("/p /h {0}", "c:\log\test.pdf")
    info.CreateNoWindow = True
    info.WindowStyle = ProcessWindowStyle.Hidden
    info.UseShellExecute = False

    Dim p As Process = Process.Start(info)
    p.StartInfo.WindowStyle = ProcessWindowStyle.Hidden

    Dim counter As Integer = 0
    Do Until p.HasExited
        System.Threading.Thread.Sleep(1000)
        counter += 1
        If counter = 5 Then
            Exit Do
        End If
    Loop
    If p.HasExited = False Then
        p.CloseMainWindow()
        p.Kill()
    End If

問題一

您也許可以在注冊表中使用自己的方式。 HKEY_CLASSES_ROOT\\.pdf\\PersistentHandler\\(Default)您應該找到一個 CLSID,該 CLSID 指向在兩個位置之一找到的值。 相同密鑰的 CLSID 文件夾,或者(對於 64 位系統)在Wow6432Node\\CLSID向下一級然后在CLSID 的密鑰中。

在該鍵中,您可以查找LocalServer32並找到指向當前 exe 路徑的默認字符串值。

我不是 100% 的,但似乎有道理(盡管您將不得不在多個環境中進行驗證以確認實際上找到了您正在尋找的進程)。

(這里是有關PersistentHandlers 的注冊表項的文檔)

問題二

可能使用CreateNoWindow過程的StartInfo的。

Process p = new Process();
p.StartInfo.FileName = @"C:\Program Files (x86)\Adobe\Reader 10.0\Reader\AcroRd32.exe";
p.StartInfo.Arguments = "/t \"Label.pdf\" \"HP4000\" \"HP LaserJet 4100 Series PCL6\" \"out.pdf\"";
p.CreateNoWindow = true;
p.Start();
p.WaitForExit();

(不過只是一個猜測,但我相信一些測試會證明它有效/無效)

如果您使用 Acrobat reader 4.0,您可以執行以下操作:"C:\\Program Files\\Adobe\\Acrobat 4.0\\Reader\\Acrord32.exe" /t /s "U:\\PDF_MS\\SM003067K08.pdf" Planning_H2 BUT 如果 PDF文件已在較新版本的 Acrobat 中創建,一個不可見的窗口打開

您已經嘗試過與 Acrobat Reader 不同的東西,所以我的建議是忘記 GUI 應用程序並使用 3rd 方命令行工具,如 RawFilePrinter.exe

private static void ExecuteRawFilePrinter() {
    Process process = new Process();
    process.StartInfo.FileName = "c:\\Program Files (x86)\\RawFilePrinter\\RawFilePrinter.exe";
    process.StartInfo.WindowStyle = ProcessWindowStyle.Hidden;
    process.StartInfo.Arguments = string.Format("-p \"c:\\Users\\Me\\Desktop\\mypdffile.pdf\" \"Canon Printer\"");

    process.Start();
    process.WaitForExit();
    if (process.ExitCode == 0) {
            //ok
    } else {
            //error
    }
}

最新版本下載: https : //bigdotsoftware.pl/rawfileprinter

對於問題 2

使用/h參數將在最小化窗口中打開 Acrobat 或 Adob​​e Reader。

示例: C:\\Program Files (x86)\\Adobe\\Reader 10.0\\Reader>AcroRd32.exe **/h** /t "Label.pdf" "HP4000" "HP LaserJet 4100 Series PCL6" "out.pdf"

相關文檔: https : //www.adobe.com/content/dam/acom/en/devnet/acrobat/pdfs/Acrobat_SDK_developer_faq.pdf#page=24

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM