Как я могу послать документ на принтер и он печатает?


вот основная предпосылка:

мой пользователь нажимает некоторые штуковины, и PDF-файл выплевывается на его рабочий стол. Есть ли способ отправить этот файл в очередь принтера и распечатать его на локально подключенном принтере?

string filePath = "filepathisalreadysethere";
SendToPrinter(filePath); //Something like this?

Он будет совершать этот процесс много раз. Для каждого студента в классе он должен распечатать небольшой табель успеваемости. Поэтому я создаю PDF для каждого студента, и я хотел бы автоматизировать процесс печати вместо того, чтобы создавать pdf-файл пользователя, печать, генерация pdf, печать, генерация pdf, печать.

какие-либо предложения о том, как подойти к этому? Я работаю на Windows XP с Windows Forms .NET 4.

Я нашел этот вопрос StackOverflow, где принятый ответ предполагает:

после того как вы создали ваши файлы, вы можно распечатать их с помощью командной строки (вы может использовать класс команд, найденный в система.Пространство имен диагностики для это)

Как бы я выполнил это?

11 57

11 ответов:

вы можете сказать Acrobat Reader, чтобы распечатать файл, используя (как кто-то уже упоминал здесь) команду "print". После этого Вам также нужно будет закрыть Acrobat Reader программно:

private void SendToPrinter()
{
   ProcessStartInfo info = new ProcessStartInfo();
   info.Verb = "print";
   info.FileName = @"c:\output.pdf";
   info.CreateNoWindow = true;
   info.WindowStyle = ProcessWindowStyle.Hidden;

   Process p = new Process();
   p.StartInfo = info;
   p.Start();

   p.WaitForInputIdle();
   System.Threading.Thread.Sleep(3000);
   if (false == p.CloseMainWindow())
      p.Kill();
}

Это открывает Acrobat Reader и говорит ему отправить PDF на принтер по умолчанию, а затем выключает Acrobat через три секунды.

Если вы готовы поставлять другие продукты с вашим приложением, то вы можете использовать GhostScript (бесплатно) или PDF-принтер командной строки например,http://www.commandlinepdf.com/ (коммерческий).

Примечание: пример кода открывает PDF в текущее приложение, зарегистрированное для печати PDF-файлов, который является Adobe Acrobat Reader на большинстве машин людей. Однако возможно, что они используют другой просмотрщик PDF, такой как Foxit (http://www.foxitsoftware.com/pdf/reader/). пример кода все равно должен работать.

добавление нового ответа на этот вопрос, поскольку вопрос о печати PDF в .net существует уже давно, и большинство ответов предшествуют библиотеке Google Pdfium, которая теперь имеет оболочку .net. Для меня я сам исследовал эту проблему и продолжал придумывать пустые, пытаясь сделать хакерские решения, такие как spawning Acrobat или другие читатели PDF, или запуск в коммерческие библиотеки, которые дороги и не очень совместимы с условиями лицензирования. Но библиотека Google Pdfium и PdfiumViewer .net wrapper являются открытым исходным кодом, поэтому являются отличным решением для многих разработчиков, включая меня. PdfiumViewer лицензируется под лицензией Apache 2.0.

вы можете получить пакет NuGet здесь:

https://www.nuget.org/packages/PdfiumViewer/

и вы можете найти исходный код здесь:

https://github.com/pvginkel/PdfiumViewer

вот простой код, который будет молча печатать любое количество копии PDF файл с его именем. Вы также можете загрузить PDF-файлы из потока (как мы обычно это делаем), и вы можете легко понять это, глядя на код или примеры. Существует также представление файла WinForm PDF, так что вы также можете отобразить PDF-файлы в виде или сделать предварительный просмотр на них. Для нас мне просто нужен был способ молча распечатать PDF-файл на определенном принтере по требованию.

public bool PrintPDF(
    string printer,
    string paperName,
    string filename,
    int copies)
{
    try {
        // Create the printer settings for our printer
        var printerSettings = new PrinterSettings {
            PrinterName = printer,
            Copies = (short)copies,
        };

        // Create our page settings for the paper size selected
        var pageSettings = new PageSettings(printerSettings) {
            Margins = new Margins(0, 0, 0, 0),
        };
        foreach (PaperSize paperSize in printerSettings.PaperSizes) {
            if (paperSize.PaperName == paperName) {
                pageSettings.PaperSize = paperSize;
                break;
            }
        }

        // Now print the PDF document
        using (var document = PdfDocument.Load(filename)) {
            using (var printDocument = document.CreatePrintDocument()) {
                printDocument.PrinterSettings = printerSettings;
                printDocument.DefaultPageSettings = pageSettings;
                printDocument.PrintController = new StandardPrintController();
                printDocument.Print();
            }
        }
        return true;
    } catch {
        return false;
    }
}

Я знаю, что тег говорит Windows Forms... но, если кто-то заинтересован в WPF способ применения System.Printing работает как шарм.

var file = File.ReadAllBytes(pdfFilePath);
var printQueue = LocalPrintServer.GetDefaultPrintQueue();

using (var job = printQueue.AddJob())
using (var stream = job.JobStream)
{
    stream.Write(file, 0, file.Length);
}

только не забудьте включить System.Printing ссылка, если она еще не включена. Теперь, этот метод не играет хорошо с ASP.NET или Windows Service. Он не должен использоваться с Windows Forms, а это System.Drawing.Printing. У меня нет ни одной проблемы с моей печатью PDF, используя приведенный выше код.

Я должен упомянуть, однако, что если ваш принтер не поддерживает прямую печать для формата PDF-файла, вам не повезло с этим методом.

это слегка измененное решение. Процесс будет убит, когда он простаивал в течение не менее 1 секунды. Возможно, вам следует добавить время X секунд и вызвать функцию из отдельного потока.

private void SendToPrinter()
{
  ProcessStartInfo info = new ProcessStartInfo();
  info.Verb = "print";
  info.FileName = @"c:\output.pdf";
  info.CreateNoWindow = true;
  info.WindowStyle = ProcessWindowStyle.Hidden;

  Process p = new Process();
  p.StartInfo = info;
  p.Start();

  long ticks = -1;
  while (ticks != p.TotalProcessorTime.Ticks)
  {
    ticks = p.TotalProcessorTime.Ticks;
    Thread.Sleep(1000);
  }

  if (false == p.CloseMainWindow())
    p.Kill();
}

следующий фрагмент кода-это адаптация Кендалл Беннетт код для печати pdf-файлов с помощью библиотеки PdfiumViewer. Основное отличие заключается в том, что используется поток, а не файл.

public bool PrintPDF(
    string printer,
    string paperName,
    int copies, Stream stream)
        {
            try
            {
                // Create the printer settings for our printer
                var printerSettings = new PrinterSettings
                {
                    PrinterName = printer,
                    Copies = (short)copies,
                };

            // Create our page settings for the paper size selected
            var pageSettings = new PageSettings(printerSettings)
            {
                Margins = new Margins(0, 0, 0, 0),
            };
            foreach (PaperSize paperSize in printerSettings.PaperSizes)
            {
                if (paperSize.PaperName == paperName)
                {
                    pageSettings.PaperSize = paperSize;
                    break;
                }
            }

            // Now print the PDF document
            using (var document = PdfiumViewer.PdfDocument.Load(stream))
            {
                using (var printDocument = document.CreatePrintDocument())
                {
                    printDocument.PrinterSettings = printerSettings;
                    printDocument.DefaultPageSettings = pageSettings;
                    printDocument.PrintController = new StandardPrintController();
                    printDocument.Print();
                }
            }
            return true;
        }
        catch (System.Exception e)
        {
            return false;
        }
    }

в моем случае я создаю PDF-файл с помощью библиотеки под названием PdfSharp, а затем сохраняю документ в поток следующим образом:

        PdfDocument pdf = PdfGenerator.GeneratePdf(printRequest.html, PageSize.A4);
        pdf.AddPage();

        MemoryStream stream = new MemoryStream();
        pdf.Save(stream);
        MemoryStream stream2 = new MemoryStream(stream.ToArray());

одна вещь, которую я хочу отметить, что может быть полезно для других разработчиков является то, что я пришлось установить 32-разрядную версию pdfuim native dll для того, чтобы печать работала, даже если я использую Windows 10 64 бит. Я установил следующие два пакета NuGet с помощью диспетчера пакетов NuGet в Visual Studio:

  • PdfiumViewer
  • PdfiumViewer.Родной.архитектуры x86.v8-xfa

самый простой способ:

var pi=new ProcessStartInfo("C:\file.docx");
pi.UseShellExecute = true;
pi.Verb = "print";
var process =  System.Diagnostics.Process.Start(pi);

это поздний ответ, но вы также можете использовать файл.Метод копирования System.IO пространство имен top отправить файл на принтер:

System.IO.File.Copy(filename, printerName);

Это хорошо

Я знаю, что Эдвин ответил на него выше, но он печатает только один документ. Я использую этот код для печати всех файлов из данного каталога.

public void PrintAllFiles()
{
    System.Diagnostics.ProcessStartInfo info = new System.Diagnostics.ProcessStartInfo();
    info.Verb = "print";
    System.Diagnostics.Process p = new System.Diagnostics.Process();
    //Load Files in Selected Folder
    string[] allFiles = System.IO.Directory.GetFiles(Directory);
    foreach (string file in allFiles)
    {
        info.FileName = @file;
        info.CreateNoWindow = true;
        info.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;
         p.StartInfo = info;
        p.Start();
    }
    //p.Kill(); Can Create A Kill Statement Here... but I found I don't need one
    MessageBox.Show("Print Complete");
}

он по существу циклически проходит через каждый файл в данном каталоге переменной каталога - > для меня это было @"C:\Users\Owner\Documents\SalesVaultTesting" и распечатывает эти файлы на ваш принтер по умолчанию.

вы можете использовать DevExpress PdfDocumentProcessor.Print (PdfPrinterSettings) метод.

public void Print(string pdfFilePath)
{
      if (!File.Exists(pdfFilePath))
          throw new FileNotFoundException("No such file exists!", pdfFilePath);

      // Create a Pdf Document Processor instance and load a PDF into it.
      PdfDocumentProcessor documentProcessor = new PdfDocumentProcessor();
      documentProcessor.LoadDocument(pdfFilePath);

      if (documentProcessor != null)
      {
          PrinterSettings settings = new PrinterSettings();

          //var paperSizes = settings.PaperSizes.Cast<PaperSize>().ToList();
          //PaperSize sizeCustom = paperSizes.FirstOrDefault<PaperSize>(size => size.Kind == PaperKind.Custom); // finding paper size

          settings.DefaultPageSettings.PaperSize = new PaperSize("Label", 400, 600);

          // Print pdf
          documentProcessor.Print(settings);
      }
}