How to determine whether a local printer is Online? (1 Viewer)

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
Hi All...

So, i have a routine that enables me to select a report from a populated ListBox then print it to a specific printer of choice .. Works fine for both physical & virtual printers..

I am anticipating the end user is not computer savvy therefore i wish to prevent the end user selecting a printer that is not active.

I have been Googling and have not found anything specific but have found a link to something that may help which is in VB:-

Before i try convert this to VBA has anyone identified a simple method to do this?

Thanks in advance..
 

Attachments

  • frmPrintReport.jpg
    frmPrintReport.jpg
    406.3 KB · Views: 424

arnelgp

..forever waiting... waiting for jellybean!
Local time
Today, 19:23
Joined
May 7, 2009
Messages
19,234
see this thead about different
"local" printer status:
c# - Using ManagementObjectSearcher and Win32_Printer to check Status - Stack Overflow
Code:
Public Function getDefaultPrinter() As String
    Dim computer            As String
    Dim wmiService          As Object
    Dim installedPrinters   As Variant
    Dim printer             As Object
    Dim i                   As Integer
On Error Resume Next
    'Set the computer. Dot means the computer running the code.
    computer = "."
    
    'Get the WMI object
    Set wmiService = GetObject("winmgmts:" & "{impersonationLevel=impersonate}!\\" & computer & "\root\cimv2")
    
    'Retrieve information about the installed printers (by running a query).
    Set installedPrinters = wmiService.ExecQuery("Select * from Win32_Printer")
        
    'If an error occurs in the previous step, inform the user.
    If Err.Number <> 0 Then
        MsgBox "Could not retrieve the printer information from WMI object!", vbCritical, "WMI Object Error"
        Exit Function
    End If
    'Loop through all the installed printers and get their name. Check if one of them is the default one.
    'Printer status
    'Other (1)
    'Unknown (2)
    'Idle (3)
    'Printing (4)
    'Warmup (5)
    'Stopped Printing(6)
    'Offline (7)
    For Each printer In installedPrinters
        'Write the results to the worksheet.
        Debug.Print printer.Name, printer.PrinterStatus, printer.Local
        If (printer.Default) Then
            getDefaultPrinter = printer.Name
            'Exit For
        End If
    Next printer

End Function
 

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
see this thead about different
"local" printer status:
c# - Using ManagementObjectSearcher and Win32_Printer to check Status - Stack Overflow
Code:
Public Function getDefaultPrinter() As String
    Dim computer            As String
    Dim wmiService          As Object
    Dim installedPrinters   As Variant
    Dim printer             As Object
    Dim i                   As Integer
On Error Resume Next
    'Set the computer. Dot means the computer running the code.
    computer = "."
  
    'Get the WMI object
    Set wmiService = GetObject("winmgmts:" & "{impersonationLevel=impersonate}!\\" & computer & "\root\cimv2")
  
    'Retrieve information about the installed printers (by running a query).
    Set installedPrinters = wmiService.ExecQuery("Select * from Win32_Printer")
      
    'If an error occurs in the previous step, inform the user.
    If Err.Number <> 0 Then
        MsgBox "Could not retrieve the printer information from WMI object!", vbCritical, "WMI Object Error"
        Exit Function
    End If
    'Loop through all the installed printers and get their name. Check if one of them is the default one.
    'Printer status
    'Other (1)
    'Unknown (2)
    'Idle (3)
    'Printing (4)
    'Warmup (5)
    'Stopped Printing(6)
    'Offline (7)
    For Each printer In installedPrinters
        'Write the results to the worksheet.
        Debug.Print printer.Name, printer.PrinterStatus, printer.Local
        If (printer.Default) Then
            getDefaultPrinter = printer.Name
            'Exit For
        End If
    Next printer

End Function

I appreciate your reply, I'm missing something somewhere. I am getting a result of "True" for all printers including a printer that is not turned on therefore I'm questioning what the True value actually represents. Sure, all the virtual printers give a result of "True" as expected. Maybe It seems i need to check one or more values per printer to encourage an accurate result. From the code offered above Maybe 'Idle (3) 'Printing (4) 'Warmup (5), a combination of the 3 or maybe just the Offline (7).

My Process:-

Code to Select a printer( Done Working)
Code to change Current Printer (Done Working)
Code to inspect the chosen printer name to see if either (3) or (4) or (4) or (All) or (7) and depending on result throw a message giving status.

Regards...
 

arnelgp

..forever waiting... waiting for jellybean!
Local time
Today, 19:23
Joined
May 7, 2009
Messages
19,234
did you see Debug.Print? the last part test if the Printer Is Local, therefore True.
 

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
did you see Debug.Print? the last part test if the Printer Is Local, therefore True.
HI,

Maybe i haven't made it clear or my lack of knowledge is showing through lol.
I'm not checking to see if a printer is local but whether the printer status is any of the (1 to 7) results in a printer status.

Maybe this is something that will give me what i'm after. It seems others have struggled too lol

 
Last edited:

arnelgp

..forever waiting... waiting for jellybean!
Local time
Today, 19:23
Joined
May 7, 2009
Messages
19,234
See again the debug.
What i am ouputting is:
1.Printer name
2.PrinterStatus (3 idle)
3.Local? True
 

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
See again the debug.
What i am ouputting is:
1.Printer name
2.PrinterStatus (3 idle)
3.Local? True
Sorry arneigp...

As you can see i have much to learn....

You code refers to writing the output to a worksheet... I'm using Access VBA..
Don't understand the Debug.Print thingy...
I just want the result to be represented in something like a messagebox "The Printer xxx you have selected is yyy" where xxx is the printer name and yyy represents a predetermined string referring to the status code..
 

Gasman

Enthusiastic Amateur
Local time
Today, 12:23
Joined
Sep 21, 2011
Messages
14,269
To be fair, this is what I get when I run that function and I have no printer switched on.?
I only have the one actual printer anyway, the brother and that is a wifi printer.?

Code:
? getdefaultprinter
Send To OneNote 2007    3   True
OneNote for Windows 10  3   True
Microsoft XPS Document Writer   3   True
Microsoft Print to PDF  3   True
Fax 3   True
CutePDF Writer  3   True
Canon MG3600 series Printer WS  1   True
Brother PC-FAX v.3.2    3   True
Brother MFC-L2700DW series Printer  1   True
Brother MFC-L2700DW series  3   True
AnyDesk Printer 3   True
Brother MFC-L2700DW series Printer

When switched on ready to print, I get
Code:
? getdefaultprinter
Send To OneNote 2007    3   True
OneNote for Windows 10  3   True
Microsoft XPS Document Writer   3   True
Microsoft Print to PDF  3   True
Fax 3   True
CutePDF Writer  3   True
Canon MG3600 series Printer WS  1   True
Brother PC-FAX v.3.2    3   True
Brother MFC-L2700DW series Printer  1   True
Brother MFC-L2700DW series  3   True
AnyDesk Printer 3   True
Brother MFC-L2700DW series Printer
1632746094016.png
 

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
To be fair, this is what I get when I run that function and I have no printer switched on.?
I only have the one actual printer anyway, the brother and that is a wifi printer.?

Code:
? getdefaultprinter
Send To OneNote 2007    3   True
OneNote for Windows 10  3   True
Microsoft XPS Document Writer   3   True
Microsoft Print to PDF  3   True
Fax 3   True
CutePDF Writer  3   True
Canon MG3600 series Printer WS  1   True
Brother PC-FAX v.3.2    3   True
Brother MFC-L2700DW series Printer  1   True
Brother MFC-L2700DW series  3   True
AnyDesk Printer 3   True
Brother MFC-L2700DW series Printer

When switched on ready to print, I get
Code:
? getdefaultprinter
Send To OneNote 2007    3   True
OneNote for Windows 10  3   True
Microsoft XPS Document Writer   3   True
Microsoft Print to PDF  3   True
Fax 3   True
CutePDF Writer  3   True
Canon MG3600 series Printer WS  1   True
Brother PC-FAX v.3.2    3   True
Brother MFC-L2700DW series Printer  1   True
Brother MFC-L2700DW series  3   True
AnyDesk Printer 3   True
Brother MFC-L2700DW series Printer
View attachment 94860
Hi,

Yes, I'm getting the same result... 3 even if printer is turned off and this is also a Wi-Fi Printer (Canon)... Maybe we can make use of the spool library:-
 

Attachments

  • Test Printer Status VB.zip
    5.3 KB · Views: 443
  • ScreenShotPrinters.jpg
    ScreenShotPrinters.jpg
    186.3 KB · Views: 430

The_Doc_Man

Immoderate Moderator
Staff member
Local time
Today, 06:23
Joined
Feb 28, 2001
Messages
27,172
FYI, the "debug.print" thingy is a popular, almost NECESSARY, debugging tool used to have Access tell you the value of something at the point of execution of that Debug.Print method. And the answer of the "what is your status?" question asked by Debug.Print is printed to the IMMEDIATE window, one of the options in the VBA code window, one of the things you can view.

Once you learn how to use this useful debugging tool, you will learn to love it for not only WHAT it tells you, but WHEN. However, you are right that if you are inexperienced, you might not be familiar with it. Don't worry, you'll get used to it. We all did.
 

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
FYI, the "debug.print" thingy is a popular, almost NECESSARY, debugging tool used to have Access tell you the value of something at the point of execution of that Debug.Print method. And the answer of the "what is your status?" question asked by Debug.Print is printed to the IMMEDIATE window, one of the options in the VBA code window, one of the things you can view.

Once you learn how to use this useful debugging tool, you will learn to love it for not only WHAT it tells you, but WHEN. However, you are right that if you are inexperienced, you might not be familiar with it. Don't worry, you'll get used to it. We all did.
Hi,

Yes; its definitely something i need to lookup.. Just by looking at Gasman reply i can now see why its absolutely necessary. I cannot believe how far I've got without it lol.. Will spend a few weeks getting familiar with it for sure...
 

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
To be fair, this is what I get when I run that function and I have no printer switched on.?
I only have the one actual printer anyway, the brother and that is a wifi printer.?

Code:
? getdefaultprinter
Send To OneNote 2007    3   True
OneNote for Windows 10  3   True
Microsoft XPS Document Writer   3   True
Microsoft Print to PDF  3   True
Fax 3   True
CutePDF Writer  3   True
Canon MG3600 series Printer WS  1   True
Brother PC-FAX v.3.2    3   True
Brother MFC-L2700DW series Printer  1   True
Brother MFC-L2700DW series  3   True
AnyDesk Printer 3   True
Brother MFC-L2700DW series Printer

When switched on ready to print, I get
Code:
? getdefaultprinter
Send To OneNote 2007    3   True
OneNote for Windows 10  3   True
Microsoft XPS Document Writer   3   True
Microsoft Print to PDF  3   True
Fax 3   True
CutePDF Writer  3   True
Canon MG3600 series Printer WS  1   True
Brother PC-FAX v.3.2    3   True
Brother MFC-L2700DW series Printer  1   True
Brother MFC-L2700DW series  3   True
AnyDesk Printer 3   True
Brother MFC-L2
[/QUOTE]
 

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
So; been looking at this scaping the net and it seems hell of a job just to get the true print ready status of a printer....
Why its made so difficult i have no idea :mad:but the amount of time i need to invest in this to get a solution cannot be justified...
Especially when i need to learn how to use the debugging tool lol :)
May come back to it at the end of the project as its a nicety not a necessity...

Thanks for all the help/advice offered(y)

Regards..
 

Gasman

Enthusiastic Amateur
Local time
Today, 12:23
Joined
Sep 21, 2011
Messages
14,269
Well good luck, as I just did a quick google (sometimes it is the words that fail to find anything) and I found an Excel link

Code is
Code:
Function IsPrinterReady(Optional strPrinter As String = "") As Boolean

'Returns True if printer is turned on and ready.

'If no strPrintername provided, active printer is assumed.

'VBA code by Mor Sagmon

 

    If (strPrinter = "") Then strPrinter = Application.printer

    IsPrinterReady = False

   

    'If strPrinter has port part - discard

    Dim intOnPosition As Integer

    intOnPosition = InStr(1, strPrinter, " on ")

    If (intOnPosition > 0) Then

        strPrinter = Left(strPrinter, intOnPosition - 1)

    Else

        intOnPosition = InStr(1, strPrinter, " " & Chr(225)) 'Replace 225 with ASCII code as per your own Windows language.

        If (intOnPosition > 0) Then

            strPrinter = Left(strPrinter, intOnPosition - 1)

        End If

    End If

  

    On Error GoTo FailedPrinter

    IsPrinterReady = Not GetObject("winmgmts:\\.\root\CIMV2").Get("Win32_Printer='" & strPrinter & "'").WorkOffline

    Exit Function

FailedPrinter:

   'Implement error handling here if necessary

End Function

I added that to arnel's code where he Debug.prints the values and it always returned True, yet the printer is off?

 

Jason Lee Hayes

Active member
Local time
Today, 12:23
Joined
Jul 25, 2020
Messages
175
Well good luck, as I just did a quick google (sometimes it is the words that fail to find anything) and I found an Excel link

Code is
Code:
Function IsPrinterReady(Optional strPrinter As String = "") As Boolean

'Returns True if printer is turned on and ready.

'If no strPrintername provided, active printer is assumed.

'VBA code by Mor Sagmon



    If (strPrinter = "") Then strPrinter = Application.printer

    IsPrinterReady = False

  

    'If strPrinter has port part - discard

    Dim intOnPosition As Integer

    intOnPosition = InStr(1, strPrinter, " on ")

    If (intOnPosition > 0) Then

        strPrinter = Left(strPrinter, intOnPosition - 1)

    Else

        intOnPosition = InStr(1, strPrinter, " " & Chr(225)) 'Replace 225 with ASCII code as per your own Windows language.

        If (intOnPosition > 0) Then

            strPrinter = Left(strPrinter, intOnPosition - 1)

        End If

    End If

 

    On Error GoTo FailedPrinter

    IsPrinterReady = Not GetObject("winmgmts:\\.\root\CIMV2").Get("Win32_Printer='" & strPrinter & "'").WorkOffline

    Exit Function

FailedPrinter:

   'Implement error handling here if necessary

End Function

I added that to arnel's code where he Debug.prints the values and it always returned True, yet the printer is off?

Hi,

Yes, i spotted this code as well and did the same. as you... I think we have to communicate with the spool library to get true results...

Regards...
 

isladogs

MVP / VIP
Local time
Today, 12:23
Joined
Jan 14, 2017
Messages
18,216
I just tried the code that @arnelgp supplied.

1632765952887.png

It correctly identifies the default printer (the only 'real' printer in the list) but reports it as 2 (unknown) whether or not it is switched on & ready to print.
I then found an item sitting in the EPSON print queue and removed it.
The printer status was then shown as 3 like all the rest whether or not it was switched on

Just wondering - has anyone checked whether those printer status values are correct? I haven't done so
 

isladogs

MVP / VIP
Local time
Today, 12:23
Joined
Jan 14, 2017
Messages
18,216
Just tested collecting all the properties for each printer using WMI. There are over 80 such properties including default & workoffline
I modified the code as follows, omitting printerStatus as it seems to be meaningless:

Code:
Public Function getDefaultPrinter() As String
    Dim computer            As String
    Dim wmiService          As Object
    Dim installedPrinters   As Variant
    Dim printer             As Object
    Dim i                   As Integer
On Error Resume Next
    'Set the computer. Dot means the computer running the code.
    computer = "."
    
    'Get the WMI object
    Set wmiService = GetObject("winmgmts:" & "{impersonationLevel=impersonate}!\\" & computer & "\root\cimv2")
    
    'Retrieve information about the installed printers (by running a query).
    Set installedPrinters = wmiService.ExecQuery("Select * from Win32_Printer")
        
    'If an error occurs in the previous step, inform the user.
    If Err.Number <> 0 Then
        MsgBox "Could not retrieve the printer information from WMI object!", vbCritical, "WMI Object Error"
        Exit Function
    End If
    'Loop through all the installed printers and get their name. Check if one of them is the default one.
    'Printer status - NOT USED
    'Other (1)
    'Unknown (2)
    'Idle (3)
    'Printing (4)
    'Warmup (5)
    'Stopped Printing(6)
    'Offline (7)
    For Each printer In installedPrinters
        'Write the results to the immediate window
       ' Debug.Print printer.Name, printer.PrinterStatus, printer.Local
        Debug.Print printer.Name, "Local: " & printer.Local & "," & vbTab & "Default: " & printer.Default & _
            "," & vbTab & "Work Offline: " & printer.workoffline
        If (printer.Default) Then
            getDefaultPrinter = printer.Name
            Debug.Print "====================" & vbCrLf & "Default printer = " & getDefaultPrinter
            'Exit For
        End If
    Next printer

End Function

That gave me this output in the immediate window:
Code:
Send To OneNote 2010        Local: True,    Default: False, Work Offline: False
OneNote for Windows 10      Local: True,    Default: False, Work Offline: False
OneNote (Desktop)           Local: True,    Default: False, Work Offline: False
Microsoft XPS Document Writer             Local: True,    Default: False, Work Offline: False
Microsoft Print to PDF      Local: True,    Default: False, Work Offline: False
Fax           Local: True,    Default: False, Work Offline: False
EPSON AL-C1600              Local: True,    Default: True,  Work Offline: True
====================
Default printer = EPSON AL-C1600

Does that help at all?
 

Isaac

Lifelong Learner
Local time
Today, 04:23
Joined
Mar 14, 2017
Messages
8,777
I wonder (out loud) whether a person could simply test whether or not this command:
Code:
Application.PrintCommunication = True

... errs out, or not.

Where Application is an excel application - but still, it's 2 lines of code, which is nice.

Technically, according to MS, whether or not you can set this to True ought to depend on whether the default printer is online.

But, I'm not completely sure it will always work as advertised ... Just a thought to try if you're interested.
 

isladogs

MVP / VIP
Local time
Today, 12:23
Joined
Jan 14, 2017
Messages
18,216
Not valid in Access

1632785821887.png


However, you can of course do both of these:
Code:
?Application.Printers.Count
7

?Application.Printer.DeviceName
EPSON AL-C1600

The DeviceName gives the default printer but there isn't a property to indicate whether it is switched on !
 
Last edited:

The_Doc_Man

Immoderate Moderator
Staff member
Local time
Today, 06:23
Joined
Feb 28, 2001
Messages
27,172
In further researching this question, I noted that perhaps you don't want to look at the printer, you want to look at the driver for the printer.


The code looks similar but you need to query the driver rather than the printer to determine status. There is a code snippet in the linked article.
 

Users who are viewing this thread

Top Bottom