Click here to Skip to main content
15,868,292 members
Articles / Desktop Programming / Windows Forms

POS Printing: The Easy Way

Rate me:
Please Sign up or sign in to vote.
4.89/5 (14 votes)
16 Sep 2010CPOL2 min read 187.1K   12.5K   28   54
VB6 Printer object supports printing to POS printers too. In this article, we will see Why and How.

Introduction

This is a class that helps developers in designing POS printing forms the easy way. Developers can add images (Logos, Ads, etc.); can use any language with any direction (RTL, LTR) easily; and can use print preview to save paper printed for testing.

Background

POS printing using the EPS/POS standard has proved difficult, after spending days of designing the printing class; I couldn't write Arabic text for unknown reasons. Printing images needed tons of code, and print-previewing was almost impossible since you might need to build an engine to parse those specific standard codes to display them on the screen.

A much easier solution was to use the classic VB printer object, those unfamiliar with the printer object can read more about it here.

To use the good old printer class of VB 6.0 in your VB.NET code, you will need to use the PowerPack compatibility library, which can be downloaded here.

Using the Code

Start by adding Microsoft.VisualBasic.PowerPacks to the references of the project.

Some imports will be needed throughout the code:

VB.NET
Imports System.Drawing
Imports Microsoft.VisualBasic.PowerPacks.Printing.Compatibility.VB6 

Some declarations and needed Enums:

VB.NET
Private p As Printer
Private _Path As String
Private _Align As TextAlignment = TextAlignment.Default
Private bIsDebug As Boolean = True
Public Enum TextAlignment As Byte
	[Default] = 0
	Left
	Center
	Right
End Enum 

Now the class constructors takes the printer name as parameters, and also the Application path for constructing the path of images to be used (if any), you can pass the Application.StartupPath for that.

VB.NET
 #Region "Constructors"
 Public Sub New(ByVal AppPath As String)
		SetPrinterName("GP-80220II (USB2)", AppPath)
	End Sub
	Public Sub New(ByVal strPrinterName As String, ByVal AppPath As String)
		SetPrinterName(strPrinterName, AppPath)
	End Sub
	Private Sub SetPrinterName(ByVal PrinterName As String, ByVal AppPath As String)
		Dim prnPrinter As Printer

		For Each prnPrinter In Printers
			If prnPrinter.DeviceName = PrinterName Then
				p = prnPrinter
				Exit For
			End If
		Next
		p.DocumentName = "ERP System"
		Me.Path = AppPath
		If bIsDebug Then
			p.PrintAction = Printing.PrintAction.PrintToPreview
		End If
	End Sub
#End Region

I used the following font sizes which were appropriate for my case. Feel free to change that as appropriate to yours:

  • Normal Font: 9.5
  • Large Font: 15
  • Small Font: 6

The following code shows properties to control fonts:

VB.NET
#Region "Font"
 	Public Property Alignment() As TextAlignment
		Get
			Return _Align
		End Get
		Set(ByVal value As TextAlignment)
			_Align = value
		End Set
	End Property
	Public Sub AlignLeft()
		_Align = TextAlignment.Left
	End Sub
	Public Sub AlignCenter()
		_Align = TextAlignment.Center
	End Sub
	Public Sub AlignRight()
		_Align = TextAlignment.Right
	End Sub
	Public Property FontName() As String
		Get
			Return p.FontName
		End Get
		Set(ByVal value As String)
			p.FontName = value
		End Set
	End Property

	Public Property FontSize() As Single
		Get
			Return p.FontSize
		End Get
		Set(ByVal value As Single)
			p.FontSize = value
		End Set
	End Property
	Public Property Bold() As Boolean
		Get
			Return p.FontBold
		End Get
		Set(ByVal value As Boolean)
			p.FontBold = value
		End Set
	End Property
	Public Sub DrawLine()
		p.DrawWidth = 2
		p.Line(p.Width, p.CurrentY)
		p.CurrentY += 20 ' to move under the drawn line
	End Sub
	Public Sub NormalFont()
		Me.FontSize = 9.5F
	End Sub
	Public Sub BigFont()
		Me.FontSize = 15.0F
	End Sub
	Public Sub SmallFont()
		Me.FontSize = 6.0F
	End Sub

	Public Sub SetFont(Optional ByVal FontSize As Single = 9.5F, _
Optional ByVal FontName As String = "FontA1x1", _
Optional ByVal BoldType As Boolean = False)
		Me.FontSize = FontSize
		Me.FontName = FontName
		Me.Bold = BoldType
	End Sub
#End Region 

For image printing, I used a PrintLogo sub, but you can use a general method (like PrintImage below):

VB.NET
 #Region "Images"
 Public Property Path() As String
		Get
			Return _Path
		End Get
		Set(ByVal value As String)
			_Path = value
		End Set
	End Property
	Public Sub PrintLogo()
		Me.PrintImage(_Path & "\Logo.bmp")
	End Sub
	Private Sub PrintImage(ByVal FileName As String)
		Dim pic As Image

		pic = pic.FromFile(FileName)

		p.PaintPicture(pic, p.CurrentX, p.CurrentY)
		p.CurrentY = p.CurrentY + pic.Height
	End Sub
#End Region 

Now, for my case, I sectioned the paper into 6 sections (sixths) for easier control. This might be appropriate for your case, but if not; you can easily change that.

Also notice that my printer prints 48 characters in normal font, that is why I also sectioned the paper into 48 columns.

VB.NET
  #Region "Control"
 	Public Sub NewPage()
		p.NewPage()
	End Sub
	Public Property RTL() As Boolean
		Get
			Return p.RightToLeft
		End Get
		Set(ByVal value As Boolean)
			p.RightToLeft = value
		End Set
	End Property
	Public Sub FeedPaper(Optional ByVal nlines As Integer = 3)
		For i As Integer = 1 To nlines
			Me.WriteLine("")
		Next
	End Sub

	Public Sub GotoCol(Optional ByVal ColNumber As Integer = 0)
		Dim ColWidth As Single = p.Width / 48
		p.CurrentX = ColWidth * ColNumber
	End Sub
	Public Sub GotoSixth(Optional ByVal nSixth As Integer = 1)
		Dim OneSixth As Single = p.Width / 6
		p.CurrentX = OneSixth * (nSixth - 1)
	End Sub

	Public Sub UnderlineOn()
		p.FontUnderline = True
	End Sub
	Public Sub UnderlineOff()
		p.FontUnderline = False
	End Sub
	Public Sub EndDoc()
		p.EndDoc()
	End Sub
	Public Sub EndJob()
		Me.EndDoc()
	End Sub
	Public Sub WriteLine(ByVal Text As String)
		Dim sTextWidth As Single = p.TextWidth(Text)
		Select Case _Align
			Case TextAlignment.Default
				'do nothing
			Case TextAlignment.Left
				p.CurrentX = 0
			Case TextAlignment.Center
				p.CurrentX = (p.Width - sTextWidth) / 2
			Case TextAlignment.Right
				p.CurrentX = (p.Width - sTextWidth)
		End Select
		p.Print(Text)
	End Sub
	Public Sub WriteChars(ByVal Text As String)
		p.Write(Text)
	End Sub
	Public Sub CutPaper()
		p.NewPage()
	End Sub

#End Region 

For using the class, a sample receipt is being created, see code and resulted print.

VB.NET
Dim P As New PrinterClass(Application.StartupPath)
With P
	'Printing Logo
	.RTL = False
	.PrintLogo()

	'Printing Title
	.FeedPaper(4)
	.AlignCenter()
	.BigFont()
	.Bold = True
	.WriteLine("Sales Receipt")

	'Printing Date
	.GotoSixth(1)
	.NormalFont()
	.WriteChars("Date:")
	.WriteLine(DateTime.Now.ToString)
	.DrawLine()
	.FeedPaper(2)

	'Printing Header
	.GotoSixth(1)
	.WriteChars("#")
	.GotoSixth(2)
	.WriteChars("Description")
	.GotoSixth(5)
	.WriteChars("Count")
	.GotoSixth(6)
	.WriteChars("Total")
	.WriteLine("")
	.DrawLine()
	'.FeedPaper(1)

	'Printing Items
	.SmallFont()
	Dim i As Integer
	For i = 1 To 6
		.GotoSixth(1)
		.WriteChars(i)
		.GotoSixth(2)
		.WriteChars("Item# " & (Rnd() * 100) \ 1)
		.GotoSixth(5)
		.WriteChars(Rnd() * 10 \ 1)
		.GotoSixth(6)
		.WriteChars((Rnd() * 50 \ 1) & " JD(s)")
		.WriteLine("")
	Next

	'Printing Totals
	.NormalFont()
	.DrawLine()
	.GotoSixth(1)
	.UnderlineOn()
	.WriteChars("Total")
	.UnderlineOff()
	.GotoSixth(5)
	.WriteChars((Rnd() * 300 \ 1) & " JD(s)")
	.CutPaper()	' Can be used with real printer to cut the paper.

	'Ending the session
	.EndDoc()
End With 

Results

Code Results

Things to Notice

  • Printer name is hard coded, but it can easily be set to read from a configuration file.
  • The printer should already be defined (driver installed) to the system, especially when using the "Print Preview" (bIsDebug set to true), so that the preview window reflects the actual properties of the printer (width, font, etc.).

Points of Interest

The following points can be seen as problems in the approach and can be used for future development of the article:

  • While printing, a "print dialogue" shows, in my case (of printing small POS receipts) this happens fast enough before it disappears, but it can still prevent application input till it disappears for bigger prints.

History

  • 16th September, 2010: Initial post

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



Comments and Discussions

 
QuestionDefault Printer Pin
Talha Muneer27-Jun-21 22:09
Talha Muneer27-Jun-21 22:09 
Questionlong item names Pin
Cool Smith7-Jan-20 22:43
Cool Smith7-Jan-20 22:43 
QuestionObject reference not set to an instance of an object. ERROR Pin
besaridrizi6-Sep-19 10:34
besaridrizi6-Sep-19 10:34 
QuestionThe whole application closes after printing Pin
Member 1174530314-Apr-19 5:37
Member 1174530314-Apr-19 5:37 
AnswerRe: The whole application closes after printing Pin
Member 1174530314-Apr-19 5:53
Member 1174530314-Apr-19 5:53 
QuestionVB6 version of class Pin
Member 1375396429-Mar-18 14:47
Member 1375396429-Mar-18 14:47 
QuestionPrint a table using this class? Pin
Alvin Seliang11-Feb-18 23:47
Alvin Seliang11-Feb-18 23:47 
QuestionIs there any way.... Pin
Member 1361352512-Jan-18 21:58
Member 1361352512-Jan-18 21:58 
QuestionCopies Pin
Glen Dias6-Jun-17 2:52
Glen Dias6-Jun-17 2:52 
QuestionNumber Alignment Right Pin
gvcs4-Apr-17 9:20
gvcs4-Apr-17 9:20 
AnswerRe: Number Alignment Right Pin
BIBASWAN4-Aug-17 5:18
BIBASWAN4-Aug-17 5:18 
Questionhow to set paper size? Pin
Member 126112394-Feb-17 18:00
Member 126112394-Feb-17 18:00 
QuestionHide Printing page x of y Pin
Member 1282262919-Dec-16 18:49
Member 1282262919-Dec-16 18:49 
AnswerRe: Hide Printing page x of y Pin
Member 128226296-Jan-17 22:35
Member 128226296-Jan-17 22:35 
Questioncan i do this from vb6 only? Pin
Member 128386977-Nov-16 23:40
Member 128386977-Nov-16 23:40 
QuestionHow do I right align amout column while printig in a POS Pin
BIBASWAN21-Jun-16 4:25
BIBASWAN21-Jun-16 4:25 
AnswerRe: How do I right align amout column while printig in a POS Pin
Member 1364626525-Jul-19 16:37
Member 1364626525-Jul-19 16:37 
QuestionSYSTEM CLOSING Pin
subashcj6-Jan-16 17:18
subashcj6-Jan-16 17:18 
AnswerRe: SYSTEM CLOSING Pin
BIBASWAN23-Jun-16 5:42
BIBASWAN23-Jun-16 5:42 
QuestionText Allignment Pin
Praful I Hampannavar3-Jun-15 18:53
Praful I Hampannavar3-Jun-15 18:53 
How to align the text from particular column
Example:
_111.00
1111.00
__11.00
--------
1233.00

"_" refers to space
QuestionMargins at the top and bottom of paper Pin
Member 1160119117-Apr-15 2:33
Member 1160119117-Apr-15 2:33 
QuestionUnicode Pin
Stm2121-Mar-15 8:30
Stm2121-Mar-15 8:30 
Question"Printer Error" Pin
Ryan Saputra29-Jul-14 21:26
Ryan Saputra29-Jul-14 21:26 
AnswerRe: "Printer Error" Pin
BIBASWAN23-Jun-16 5:44
BIBASWAN23-Jun-16 5:44 
Questioncode interference problem Pin
ZiZoU3277-Feb-14 23:16
ZiZoU3277-Feb-14 23:16 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.