Share via

How to create rule in Word to print on Letterhead paper and then Plain

Anonymous
2024-01-15T11:05:01+00:00

Hi

I want to create a rule/macro that will allow me the option to choose to print my document first copy on letterhead (drawer 1) and then a plain copy follows immediately (LCF tray).

At the moment I have to print two separate documents.

Thank you.

Microsoft 365 and Office | Word | For business | Windows

Locked Question. This question was migrated from the Microsoft Support Community. You can vote on whether it's helpful, but you can't add comments or replies or follow the question.

0 comments No comments

7 answers

Sort by: Most helpful
  1. Charles Kenyon 167.1K Reputation points Volunteer Moderator
    2024-01-16T03:00:57+00:00

    Dear AdnerbCB,

    Good day!!

    I understand your concern but since your requirement is related to VBA, I would like to suggest you post your requirement in the related community i.e., VBA community to get the help from the VBA experts on your requirement. Reference: Office VBA support and feedback | Microsoft Learn

    Apologies for redirecting you to different community as the moderators in this community posted focus on the users with the out of the box concerns on Microsoft 365 and have limited knowledge on the VBA, so to get the fast and better assistance, we have redirected you in the correct path.

    Moreover, I will keep this thread open so that Word MVPs and experts in this community can share the VBA that meets your requirement.

    Appreciate your patience and understanding. Have a great day!!

    Best Regards,

    Sophia

    @Sophia,

    Sending AdnerCB elsewhere is pointless and may be harmful. See A Message to Forum Cross-Posters.

    The volunteers who answer questions here have a vast experience; and a number are very experienced vba programmers. I know that was not a requirement for your position, but the knowledge needed for answers is here.

    See Jay Freedman's post which is exemplary and is far beyond what someone could get, for instance, on StackOverflow. Many of the people answering questions in the other spots you linked are the same people who answer those questions here.

    Was this answer helpful?

    1 person found this answer helpful.
    0 comments No comments
  2. Jay Freedman 207.6K Reputation points Volunteer Moderator
    2024-01-16T02:29:23+00:00

    Is the difference between the two copies only which printer tray they use, or do you need different content (e.g., a logo or header on the plain-paper copy that doesn't appear on the letterhead copy)?

    If it's only the tray that differs, that can be handled by a simple macro. However, almost every printer manufacturer uses a different set of numbers to indicate the trays, so you need to do a bit of experimentation to find the right values for your printer. The following passage is from an article written by Jonathan West about 20 years ago (nothing about this topic has changed since then).

    
    In Word VBA, dealing with paper trays is a horrible mess. The Word object model offers the DefaultTrayID, FirstPageTray and OtherPagesTray properties. The first one is a property of the Options object, and defines the default tray used when printing from Word. The other two are properties of the PageSetup object, and are document-specific.
    
    The VBA Help for Word lists a number of constants which it suggests should be used with the DefaultTrayID, FirstPageTray and OtherPagesTray properties. These are as follows.
    
    Value Word	Constant Name
    
    0	     wdPrinterDefaultBin
    
    1	     wdPrinterOnlyBin
    
    1	     wdPrinterUpperBin
    
    2	     wdPrinterLowerBin
    
    3	     wdPrinterMiddleBin
    
    4	     wdPrinterManualFeed
    
    5	     wdPrinterEnvelopeFeed
    
    6	     wdPrinterManualEnvelopeFeed
    
    7	     wdPrinterAutomaticSheetFeed
    
    8	     wdPrinterTractorFeed
    
    9	     wdPrinterSmallFormatBin
    
    10	     wdPrinterLargeFormatBin
    
    11	     wdPrinterLargeCapacityBin
    
    14	     wdPrinterPaperCassette
    
    15	     wdPrinterFormSource
    
    Unfortunately, no two printers use quite the same names and numbers for their paper trays, and most of them do not use the numbers defined by the Word constants. 
    
    If you use the Word constants when trying to set the paper trays for these printers, in most cases absolutely nothing will happen—the tray won't change. The printer will simply ignore a request to change to a tray number that is not available.
    
    **Getting the Available Paper Bin Names and Numbers**
    
    So, we need a way of finding out what paper trays are actually available for the printer you want to use, and what their numbers are. Word VBA doesn't give you direct access to this information, but the Windows API does allow you to obtain this information from the printer driver. With careful programming, the Windows API is accessible from VBA. 
    
    The following code provides a means of getting the list of the paper bin names and numbers for the current printer. Paste it into a fresh module. Each function returns a Variant containing an array. GetBinNumbers lists the numbers, and GetBinNames lists the equivalent names for the paper bins. The code is commented so you can see what is happening at each step. If you are not familiar with VB programming of the Windows API, then it will not be at all obvious how it all works even with the comments, but I promise you, it does work! 
    
    Warning! This code makes use of a Windows API function to gain access to the printer information. Unless you are confident that you know what you are doing, messing about with the Windows API from VB or VBA is dangerous. Making a mistake in ordinary VBA will just crash your macro. Making a mistake with an API call will often bring down the whole of Word, and in a bad case even the whole of Windows, requiring a reboot. If you want to modify this code in any way, make sure you save everything first. Don't say I didn't warn you! 
    
        Option Explicit 
    
        Private Const DC_BINS = 6 
    
        Private Const DC_BINNAMES = 12 
    
        	 
    
        Private Declare Function DeviceCapabilities Lib "winspool.drv" _ 
    
        	Alias "DeviceCapabilitiesA" (ByVal lpDeviceName As String, _ 
    
        	ByVal lpPort As String, ByVal iIndex As Long, lpOutput As Any, _ 
    
        	ByVal dev As Long) As Long 
    
        Public Function GetBinNumbers() As Variant 
    
        	'Code adapted from Microsoft KB article Q194789 
    
        	'HOWTO: Determine Available PaperBins with DeviceCapabilities API 
    
        	Dim iBins As Long 
    
        	Dim iBinArray() As Integer 
    
        	Dim sPort As String 
    
        	Dim sCurrentPrinter As String 
    
        	'Get the printer & port name of the current printer 
    
        	sPort = Trim$(Mid$(ActivePrinter, InStrRev(ActivePrinter, " ") + 1)) 
    
        	sCurrentPrinter = Trim$(Left$(ActivePrinter, _ 
    
        		InStr(ActivePrinter, " on "))) 
    
        	'Find out how many printer bins there are 
    
        	iBins = DeviceCapabilities(sCurrentPrinter, sPort, _ 
    
        		DC_BINS, ByVal vbNullString, 0) 
    
        	'Set the array of bin numbers to the right size 
    
        	ReDim iBinArray(0 To iBins - 1) 
    
        	'Load the array with the bin numbers 
    
        	iBins = DeviceCapabilities(sCurrentPrinter, sPort, _ 
    
        	DC_BINS, iBinArray(0), 0) 
    
        	'Return the array to the calling routine 
    
        	GetBinNumbers = iBinArray 
    
        End Function 
    
        Public Function GetBinNames() As Variant 
    
        	'Code adapted from Microsoft KB article Q194789 
    
        	'HOWTO: Determine Available PaperBins with DeviceCapabilities API 
    
        	Dim iBins As Long 
    
        	Dim ct As Long 
    
        	Dim sNamesList As String 
    
        	Dim sNextString As String 
    
        	Dim sPort As String 
    
        	Dim sCurrentPrinter As String 
    
        	Dim vBins As Variant 
    
        	'Get the printer & port name of the current printer 
    
        	sPort = Trim$(Mid$(ActivePrinter, InStrRev(ActivePrinter, " ") + 1)) 
    
        	sCurrentPrinter = Trim$(Left$(ActivePrinter, _ 
    
        		InStr(ActivePrinter, " on "))) 
    
        	'Find out how many printer bins there are 
    
        	iBins = DeviceCapabilities(sCurrentPrinter, sPort, _ 
    
        		DC_BINS, ByVal vbNullString, 0) 
    
        	'Set the string to the right size to hold all the bin names 
    
        	'24 chars per name 
    
        	sNamesList = String(24 * iBins, 0) 
    
        	'Load the string with the bin names 
    
        	iBins = DeviceCapabilities(sCurrentPrinter, sPort, _ 
    
        		DC_BINNAMES, ByVal sNamesList, 0) 
    
        	'Set the array of bin names to the right size 
    
        	ReDim vBins(0 To iBins - 1) 
    
        	For ct = 0 To iBins - 1 
    
        		'Get each bin name in turn and assign to the next item in the array 
    
        		sNextString = Mid(sNamesList, 24 * ct + 1, 24) 
    
        		vBins(ct) = Left(sNextString, InStr(1, sNextString, Chr(0)) - 1) 
    
        	Next ct 
    
        	'Return the array to the calling routine 
    
        	GetBinNames = vBins 
    
        End Function 
    
    **Using the Code** 
    
    Fortunately, you don't need to know all the details of how that code works in order to be able to use it! It has been designed so that minimal additional code is needed when you want to manipulate the paper bins. 
    
    If you want to give the user of a VBA macro the choice of which paper bin to use, then it is necessary to display the list of bins. This is quite straightforward. Create a UserForm, and include a ListBox on it (call it ListBox1). To put the list of bin names into the ListBox, just use the following code in the UserForm\_Initialize event, so that the ListBox is filled with the list of paper trays when the UserForm is first displayed. 
    
        	ListBox1.List = GetBinNames 
    
    Later, if the user has selected a bin, and you now want to assign the selection to the current document, the following code could be used. 
    
        Dim vBinNumbers as Variant 
    
        If ListBox1.ListIndex >= 0 Then 
    
        	vBinNumbers = GetBinNumbers 
    
        	ActiveDocument.PageSetup.OtherPagesTray = _ 
    
        		vBinNumbers(ListBox1.ListIndex) 
    
        Else 
    
        	MsgBox "No paper tray has been selected." 
    
        End If 
    
    That's all there is to it! 
    
    

    <Later Edit>

    There are two major problems with the code above.

    The first is that Jonathan West wrote the article before Microsoft Office offered a 64-bit version, which is now the default installation. The code in the article uses calls to 32-bit Windows functions, which aren't compatible with 64-bit Office that runs VBA version 7. To get a version that has been modified to work in 64-bit Office, download https://jay-freedman.info/printers.zip and extract the file "Printers 64bit.bas" from the zip file. Then import the .bas file into Word's macro editor.

    The second problem is that neither version of the code works correctly with a printer that is connected to the computer by WiFi. The code expects the variable ActivePrinter to contain a printer name and port number in a particular format, which WiFi doesn't support. I haven't yet found what to substitute for the calls to the DeviceCapabilities function.

    Was this answer helpful?

    1 person found this answer helpful.
    0 comments No comments
  3. Anonymous
    2024-01-15T12:29:30+00:00

    Thank you for your reply Suzanne.

    However I don't think this is my issue - if I want to use a letterhead template for my word doc I can do that (i.e. if I only want to send letterhead letter by email without printing).

    What I'm trying to do is print a document onto 1) headed notepaper in drawer 1, and 2) simultaneously print a plain copy of that letter for my filing purposes.

    I need help to create that printing rule.

    Apologies if I've misunderstood the information you have shared.

    Was this answer helpful?

    0 comments No comments
  4. Suzanne S Barnhill 277.4K Reputation points MVP Volunteer Moderator
    2024-01-15T11:59:26+00:00

    Was this answer helpful?

    0 comments No comments
  5. Anonymous
    2024-01-15T11:52:35+00:00

    Dear AdnerbCB,

    Good day!!

    I understand your concern but since your requirement is related to VBA, I would like to suggest you post your requirement in the related community i.e., VBA community to get the help from the VBA experts on your requirement. Reference: Office VBA support and feedback | Microsoft Learn

    Apologies for redirecting you to different community as the moderators in this community posted focus on the users with the out of the box concerns on Microsoft 365 and have limited knowledge on the VBA, so to get the fast and better assistance, we have redirected you in the correct path.

    Moreover, I will keep this thread open so that Word MVPs and experts in this community can share the VBA that meets your requirement.

    Appreciate your patience and understanding. Have a great day!!

    Best Regards,

    Sophia

    Was this answer helpful?

    0 comments No comments