Pregunta

¿Existe una manera directa de enumerar todas las impresoras de red visibles en .NET? Actualmente, estoy mostrando PrintDialog para permitir al usuario seleccionar una impresora. El problema con esto es que también se muestran las impresoras locales (junto con XPS Document Writer y similares). Si puedo enumerar las impresoras de red yo mismo, puedo mostrar un cuadro de diálogo personalizado solo con esas impresoras.

¡Gracias!

¿Fue útil?

Solución

encontró este código aquí

 private void btnGetPrinters_Click(object sender, EventArgs e)
        {
// Use the ObjectQuery to get the list of configured printers
            System.Management.ObjectQuery oquery =
                new System.Management.ObjectQuery("SELECT * FROM Win32_Printer");

            System.Management.ManagementObjectSearcher mosearcher =
                new System.Management.ManagementObjectSearcher(oquery);

            System.Management.ManagementObjectCollection moc = mosearcher.Get();

            foreach (ManagementObject mo in moc)
            {
                System.Management.PropertyDataCollection pdc = mo.Properties;
                foreach (System.Management.PropertyData pd in pdc)
                {
                    if ((bool)mo["Network"])
                    {
                        cmbPrinters.Items.Add(mo[pd.Name]);
                    }
                }
            }

        }

Actualización:

" Esta función API puede enumerar todos los recursos de red, incluidos servidores, estaciones de trabajo, impresoras, recursos compartidos, directorios remotos, etc. "

http: //www.planet- source-code.com/vb/scripts/ShowCode.asp?txtCodeId=741&lngWId=10

Otros consejos

  • Obtenga la impresora predeterminada de LocalPrintServer.DefaultPrintQueue
  • Obtenga las impresoras instaladas (desde la perspectiva del usuario) de PrinterSettings.InstalledPrinters
  • Enumerar a través de la lista:
  • Cualquier impresora que comience con \\ es una impresora de red, así que obtenga la cola con new PrintServer (" \\ UNCPATH "). GetPrintQueue (" QueueName ")
  • Cualquier impresora que no comience con \\ es una impresora local, así que consígala con LocalPrintServer.GetQueue("Name")
  • Puede ver cuál es el valor predeterminado al comparar la propiedad FullName .

Nota: una impresora de red puede ser la impresora predeterminada de LocalPrintServer.DefaultPrintQueue , pero no aparece en LocalPrintServer.GetPrintQueues()

    // get available printers
    LocalPrintServer printServer = new LocalPrintServer();
    PrintQueue defaultPrintQueue = printServer.DefaultPrintQueue;

    // get all printers installed (from the users perspective)he t
    var printerNames = PrinterSettings.InstalledPrinters;
    var availablePrinters = printerNames.Cast<string>().Select(printerName => 
    {
        var match = Regex.Match(printerName, @"(?<machine>\\\\.*?)\\(?<queue>.*)");
        PrintQueue queue;
        if (match.Success)
        {
            queue = new PrintServer(match.Groups["machine"].Value).GetPrintQueue(match.Groups["queue"].Value);
        }
        else
        {
            queue = printServer.GetPrintQueue(printerName);
        }

        var capabilities = queue.GetPrintCapabilities();
        return new AvailablePrinterInfo()
        {
            Name = printerName,
            Default = queue.FullName == defaultPrintQueue.FullName,
            Duplex = capabilities.DuplexingCapability.Contains(Duplexing.TwoSidedLongEdge),
            Color = capabilities.OutputColorCapability.Contains(OutputColor.Color)
        };
    }).ToArray();

    DefaultPrinter = AvailablePrinters.SingleOrDefault(x => x.Default);

utilizando la nueva API System.Printing

using (var printServer = new PrintServer(string.Format(@"\\{0}", PrinterServerName)))
{
    foreach (var queue in printServer.GetPrintQueues())
    {
        if (!queue.IsShared)
        {
            continue;
        }
        Debug.WriteLine(queue.Name);
     }
 }

PrinterSettings.InstalledPrinters debería darle la colección que desea

En otra publicación ( https://stackoverflow.com/a/30758129/6513653 ) relacionada con esta, Scott Chamberlain dijo "No creo que haya nada en .NET que pueda hacer esto, tendrá que hacer una llamada nativa". Después de probar todos los recursos .NET posibles, creo que tiene razón. Entonces, comencé a investigar cómo el diálogo AGREGAR IMPRESORA realiza su búsqueda. Usando Wireshark, descubrí que ADD PRINTER envía al menos dos tipos de paquetes a todos los hosts en la red local: dos solicitudes http / xml al puerto 3911 y tres solicitudes SNMP. ingrese la descripción de la imagen aquí La primera solicitud SNMP es un get-next 1.3.6.1.2.1.43, que es Printer-MIB. El segundo, es un get 1.3.6.1.4.1.2699.1.2.1.2.1.1.3 que es pmPrinterIEEE1284DeviceId de PRINTER-PORT-MONITOR-MIB. Esto es lo más interesante porque es donde ADD PRINTER toma el nombre de la impresora. El tercero es un get 1.3.6.1.2.1.1.1.0, que es sysDescr del sistema SNMP MIB-2. Creo que la segunda solicitud SNMP es suficiente para encontrar la mayoría de las impresoras de red en la red local, así que hice este código. Funciona para la aplicación Windows Form y depende de SnmpSharpNet.

Editar: estoy usando ARP Ping en lugar de Ping normal para buscar hosts activos en la red. Enlace para un proyecto de ejemplo: Proyecto ListNetworks C #

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top