在.NET中获取默认打印机的最佳方法是什么?

93

我需要获取默认打印机的名称。我将使用C#,但我认为这更多是一个框架问题,而不是语言特定的问题。

7个回答

153

我发现最简单的方法是创建一个新的PrinterSettings对象。它始于所有默认值,因此您可以检查其 Name 属性以获取默认打印机的名称。

PrinterSettings在命名空间System.Drawing.Printing中的System.Drawing.dll中。

PrinterSettings settings = new PrinterSettings();
Console.WriteLine(settings.PrinterName);

或者,您可以使用静态PrinterSettings.InstalledPrinters方法获取所有打印机名称的列表,然后设置PrinterName属性并检查IsDefaultPrinter。我没有尝试过这样做,但文档似乎表明它不起作用。显然,只有当PrinterName未显式设置时,IsDefaultPrinter才为true。


6
也许值得一提的是,InstalledPrinters 返回的字符串可能与 PrinterName 属性的大小写不同。例如,在我的系统上,以下测试失败了: Dim ps As New PrinterSettings Dim foundDefault As Boolean = False For Each printer As String In PrinterSettings.InstalledPrinters If printer = ps.PrinterName Then foundDefault = True End If Next Assert.IsTrue(foundDefault) - miasbeck
1
这是对我有用的循环技术。: foreach (string name in PrinterSettings.InstalledPrinters) { PrinterSettings ps = new PrinterSettings(); ps.PrinterName = name; if (ps.IsDefaultPrinter) return name; } return null; - BrokeMyLegBiking
1
请注意,如果您将应用程序作为Windows服务运行,则此方法无法正常工作。我还没有弄清楚原因。我正在以本地服务的身份运行。 - Rudy Hinojosa
@BrokeMyLegBiking 根据 MSDN (https://msdn.microsoft.com/en-us/library/system.drawing.printing.printersettings.isdefaultprinter(v=vs.110).aspx)的说明,这个方法应该不能成功:“当你将 PrinterName 属性显式设置为非 null 的字符串值时,IsDefaultPrinter 方法始终返回 false。” - jnm2
你可以将其简化为 'string pName = new PrinterSettings().PrinterName;'。 - PKanold
1
@Rudy Hinojosa,也许这与您的问题有关?“System.Printing命名空间内的类不支持在Windows服务或ASP.NET应用程序或服务中使用。尝试从其中一个应用程序类型中使用这些类可能会产生意外问题,例如降低服务性能和运行时异常。”(MSDN文档 - jarmanso7

33

另一种方法是使用WMI(您需要添加对System.Management程序集的引用):

public static string GetDefaultPrinterName()
{
    var query = new ObjectQuery("SELECT * FROM Win32_Printer");
    var searcher = new ManagementObjectSearcher(query);

    foreach (ManagementObject mo in searcher.Get())
    {
        if (((bool?) mo["Default"]) ?? false)
        {
            return mo["Name"] as string;
        }
    }

    return null;
}

3
使用新的PrinterSettings().PrinterName有时会返回“未设置默认打印机”作为打印机名称,即使已经设置了默认打印机。纳森·波尔奇(Nathan Baulch)提供的上述WMI解决方案对我在这种情况下起了作用。 - Peter
这段代码需要引用 System.Management 并添加 using System.Management;。 - j2associates

13

如果你只想要打印机的名称,那么使用 WMI 没有任何优势。但是 WMI 能够返回许多其他打印机属性:

using System;
using System.Management;
namespace Test
{
    class Program
    {
        static void Main(string[] args)
        {
            ObjectQuery query = new ObjectQuery(
                "Select * From Win32_Printer " +
                "Where Default = True");

            ManagementObjectSearcher searcher =
                new ManagementObjectSearcher(query);

            foreach (ManagementObject mo in searcher.Get())
            {
                Console.WriteLine(mo["Name"] + "\n");

                foreach (PropertyData p in mo.Properties)
                {
                    Console.WriteLine(p.Name );
                }
            }
        }
    }
}

不仅仅是打印机,如果你对任何与计算机相关的数据感兴趣,很有可能可以通过WMI获得。 WQL(WMI版本的SQL)也是它的优势之一。


11

在这种情况下,我总是使用System.Printing.LocalPrintServer,这也可以获取打印机是本地、网络还是传真的信息。

string defaultPrinter;
using(var printServer = new LocalPrintServer()) {
  defaultPrinter = printServer.DefaultPrintQueue.FullName);
}

或者使用静态方法 GetDefaultPrintQueue

LocalPrintServer.GetDefaultPrintQueue().FullName

4

尝试这个示例

 PrinterSettings printerName = new PrinterSettings();

 string defaultPrinter;

 defaultPrinter = printerName.PrinterName;

2

这应该可以工作:

使用 System.Drawing.Printing;

PrinterSettings settings = new PrinterSettings(); string defaultPrinterName = settings.PrinterName;


0
  • 首先创建一个PrintDialog对象的实例。
  • 然后调用打印对话框对象并将PrinterName留空。这将导致Windows对象返回默认打印机名称。
  • 将其写入字符串并在调用打印程序时将其用作打印机名称。

代码:

Try

    Dim _printDialog As New System.Windows.Forms.PrintDialog

    xPrinterName = _printDialog.PrinterSettings.PrinterName '= "set as Default printer"

Catch ex As Exception
    System.Windows.Forms.MessageBox.Show("could not printed Label.", "Print Error", MessageBoxButtons.OK, MessageBoxIcon.Error)
End Try

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接