Printing reciepts with thermal printer in java
I have to print receipts through a thermal printer using Java. I have done everything. My program takes the data from the database and converts in one string using special characters, tabs and \n. Then the string is passed on to another method that converts it into graphics.
The problem is that when I click the print button, white paper comes out. I noticed that the first 4-5 characters of my String are getting printed on the last line of the bill on the right corner at the extreme end of the paper. My printer is Epson TM - T81.
public void printThisBill()
{
DefaultTableModel mod = (DefaultTableModel) jTable1.getModel();
DateFormat dateFormat = new SimpleDateFormat("dd/MM/yyyy");
DateFormat timeFormat = new SimpleDateFormat("HH:mm");
//get current date time with Date()
Date date = new Date();
Date time = new Date();
String Date = dateFormat.format(date);
String Time = timeFormat.format(time);
String Header =
" ****Super Market**** \n"
+ "Date: "+Date+" Time: "+Time+"\n"
+ "---------------------------------\n"
+ "Name Qty Rate Amt\n"
+ "---------------------------------\n";
String amt =
"\n \n \nTotal Amount = "+ amt() +"\n"
+ "Tax =" + tax() + "\n"
+ "*********************************\n"
+ "Thank you. \n";
String bill = Header;
int i = 0;
do
{
String name = ""+ mod.getValueAt(i, 2);
String qty = ""+ mod.getValueAt(i, 3);
String rate = ""+ mod.getValueAt(i, 4);
String amount = ""+ mod.getValueAt(i, 6);
if(name.length() > 12)
{
name = name.substring(0, 12)+" ";
}
else
{
for(int j= name.length()-12; j<= name.length(); j++);
{
name = name+" ";
}
}
if(qty.length()<=5)
{
for(int j= 0; j<= qty.length()-5; j++);
{
qty = qty+" ";
}
}
rate = rate;
String items =
name+"\t"+qty+"\t"+rate+"\t"+amount+"\n";
bill = bill+ items;
i++;
} while(i <= mod.getRowCount()-1);
bill = bill+amt;
System.out.println(bill);
printCard(bill);
dispose();
}
And the method that prints the bill is:
public static void printCard(final String bill )
{
Printable contentToPrint = new Printable(){
@Override
public int print(Graphics graphics, PageFormat pageFormat, int page) throws PrinterException
{
if (page > 0) {
return NO_SUCH_PAGE;
}
pageFormat.setOrientation(PageFormat.LANDSCAPE);
Graphics2D g2d = (Graphics2D)graphics.create();
g2d.setPaint(Color.black);
g2d.setFont(new Font("Arial", Font.BOLD, 10));
g2d.translate(pageFormat.getImageableX(), pageFormat.getImageableX());
g2d.drawString(bill, 0, 0);
return PAGE_EXISTS;
}
};
PrinterJob job = PrinterJob.getPrinterJob();
job.setPrintable(contentToPrint);
//You can show a print dialog before printing by job by wrapping the following blocks with a conditional statement if(job.printDialog()){...}
try
{
job.print();
} catch (PrinterException e)
{
System.err.println(e.getMessage());
}
}
What is the problem and how can I solve it? I think that I'm not setting the right parameters at drawString() Method.
Or is it something else? Any help would me appreciated.!
Solution 1:
I found this:
Java Pos Thermal Printer Example
It worked for me. No need for external libraries.
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.print.PageFormat;
import java.awt.print.Printable;
import java.awt.print.PrinterException;
import java.util.ArrayList;
import java.util.List;
import javax.print.Doc;
import javax.print.DocFlavor;
import javax.print.DocPrintJob;
import javax.print.PrintService;
import javax.print.PrintServiceLookup;
import javax.print.SimpleDoc;
import javax.print.attribute.HashPrintRequestAttributeSet;
import javax.print.attribute.PrintRequestAttributeSet;
public class PrinterService implements Printable {
public List<String> getPrinters(){
DocFlavor flavor = DocFlavor.BYTE_ARRAY.AUTOSENSE;
PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
PrintService printServices[] = PrintServiceLookup.lookupPrintServices(
flavor, pras);
List<String> printerList = new ArrayList<String>();
for(PrintService printerService: printServices){
printerList.add( printerService.getName());
}
return printerList;
}
@Override
public int print(Graphics g, PageFormat pf, int page)
throws PrinterException {
if (page > 0) { /* We have only one page, and 'page' is zero-based */
return NO_SUCH_PAGE;
}
/*
* User (0,0) is typically outside the imageable area, so we must
* translate by the X and Y values in the PageFormat to avoid clipping
*/
Graphics2D g2d = (Graphics2D) g;
g2d.translate(pf.getImageableX(), pf.getImageableY());
/* Now we perform our rendering */
g.setFont(new Font("Roman", 0, 8));
g.drawString("Hello world !", 0, 10);
return PAGE_EXISTS;
}
public void printString(String printerName, String text) {
// find the printService of name printerName
DocFlavor flavor = DocFlavor.BYTE_ARRAY.AUTOSENSE;
PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
PrintService printService[] = PrintServiceLookup.lookupPrintServices(
flavor, pras);
PrintService service = findPrintService(printerName, printService);
DocPrintJob job = service.createPrintJob();
try {
byte[] bytes;
// important for umlaut chars
bytes = text.getBytes("CP437");
Doc doc = new SimpleDoc(bytes, flavor, null);
job.print(doc, null);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
public void printBytes(String printerName, byte[] bytes) {
DocFlavor flavor = DocFlavor.BYTE_ARRAY.AUTOSENSE;
PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
PrintService printService[] = PrintServiceLookup.lookupPrintServices(
flavor, pras);
PrintService service = findPrintService(printerName, printService);
DocPrintJob job = service.createPrintJob();
try {
Doc doc = new SimpleDoc(bytes, flavor, null);
job.print(doc, null);
} catch (Exception e) {
e.printStackTrace();
}
}
private PrintService findPrintService(String printerName,
PrintService[] services) {
for (PrintService service : services) {
if (service.getName().equalsIgnoreCase(printerName)) {
return service;
}
}
return null;
}
}
And the main class:
public class Main {
public static void main(String[] args) {
PrinterService printerService = new PrinterService();
System.out.println(printerService.getPrinters());
//print some stuff. Change the printer name to your thermal printer name.
printerService.printString("EPSON-TM-T20II", "\n\n testing testing 1 2 3eeeee \n\n\n\n\n\n\n\n\n\n\n\n\n\n\n");
// cut that paper!
byte[] cutP = new byte[] { 0x1d, 'V', 1 };
printerService.printBytes("EPSON-TM-T20II", cutP);
}
}
Solution 2:
hmmm,,, i think you should use the ESC/POS commands for your printer, read the printer tech manual for Epson TM - T81. I had similar problems with TM-U220D and i wrote a class for it. This might not help as the printers are different, anyways am attaching it as a reference :
//------------------------
//-- PrinterOptions.java
//------------------------
public class PrinterOptions {
String commandSet = "";
public String initialize() {
final byte[] Init = {27, 64};
commandSet += new String(Init);
return new String(Init);
}
public String chooseFont(int Options) {
String s = "";
final byte[] ChooseFontA = {27, 77, 0};
final byte[] ChooseFontB = {27, 77, 1};
final byte[] ChooseFontC = {27, 77, 48};
final byte[] ChooseFontD = {27, 77, 49};
switch(Options) {
case 1:
s = new String(ChooseFontA);
break;
case 2:
s = new String(ChooseFontB);
break;
case 3:
s = new String(ChooseFontC);
break;
case 4:
s = new String(ChooseFontD);
break;
default:
s = new String(ChooseFontB);
}
commandSet += s;
return new String(s);
}
public String feedBack(byte lines) {
final byte[] Feed = {27,101,lines};
String s = new String(Feed);
commandSet += s;
return s;
}
public String feed(byte lines) {
final byte[] Feed = {27,100,lines};
String s = new String(Feed);
commandSet += s;
return s;
}
public String alignLeft() {
final byte[] AlignLeft = {27, 97,48};
String s = new String(AlignLeft);
commandSet += s;
return s;
}
public String alignCenter() {
final byte[] AlignCenter = {27, 97,49};
String s = new String(AlignCenter);
commandSet += s;
return s;
}
public String alignRight() {
final byte[] AlignRight = {27, 97,50};
String s = new String(AlignRight);
commandSet += s;
return s;
}
public String newLine() {
final byte[] LF = {10};
String s = new String(LF);
commandSet += s;
return s;
}
public String reverseColorMode(boolean enabled) {
final byte[] ReverseModeColorOn = {29, 66, 1};
final byte[] ReverseModeColorOff = {29, 66, 0};
String s = "";
if(enabled)
s = new String(ReverseModeColorOn);
else
s = new String(ReverseModeColorOff);
commandSet += s;
return s;
}
public String doubleStrik(boolean enabled) {
final byte[] DoubleStrikeModeOn = {27, 71, 1};
final byte[] DoubleStrikeModeOff = {27, 71, 0};
String s="";
if(enabled)
s = new String(DoubleStrikeModeOn);
else
s = new String(DoubleStrikeModeOff);
commandSet += s;
return s;
}
public String doubleHeight(boolean enabled) {
final byte[] DoubleHeight = {27, 33, 17};
final byte[] UnDoubleHeight={27, 33, 0};
String s = "";
if(enabled)
s = new String(DoubleHeight);
else
s = new String(UnDoubleHeight);
commandSet += s;
return s;
}
public String emphasized(boolean enabled) {
final byte[] EmphasizedOff={27 ,0};
final byte[] EmphasizedOn={27 ,1};
String s="";
if(enabled)
s = new String(EmphasizedOn);
else
s = new String(EmphasizedOff);
commandSet += s;
return s;
}
public String underLine(int Options) {
final byte[] UnderLine2Dot = {27, 45, 50};
final byte[] UnderLine1Dot = {27, 45, 49};
final byte[] NoUnderLine = {27, 45, 48};
String s = "";
switch(Options) {
case 0:
s = new String(NoUnderLine);
break;
case 1:
s = new String(UnderLine1Dot);
break;
default:
s = new String(UnderLine2Dot);
}
commandSet += s;
return new String(s);
}
public String color(int Options) {
final byte[] ColorRed = {27, 114, 49};
final byte[] ColorBlack = {27, 114, 48};
String s = "";
switch(Options) {
case 0:
s = new String(ColorBlack);
break;
case 1:
s = new String(ColorRed);
break;
default:
s = new String(ColorBlack);
}
commandSet += s;
return s;
}
public String finit() {
final byte[] FeedAndCut = {29, 'V', 66, 0};
String s = new String(FeedAndCut);
final byte[] DrawerKick={27,70,0,60,120};
s += new String(DrawerKick);
commandSet+=s;
return s;
}
public String addLineSeperator() {
String lineSpace = "----------------------------------------";
commandSet += lineSpace;
return lineSpace;
}
public void resetAll() {
commandSet = "";
}
public void setText(String s) {
commandSet+=s;
}
public String finalCommandSet() {
return commandSet;
}
}
feedPrinter() -- method
private static boolean feedPrinter(byte[] b) {
try {
AttributeSet attrSet = new HashPrintServiceAttributeSet(new PrinterName("EPSON TM-U220 ReceiptE4", null)); //EPSON TM-U220 ReceiptE4
DocPrintJob job = PrintServiceLookup.lookupPrintServices(null, attrSet)[0].createPrintJob();
//PrintServiceLookup.lookupDefaultPrintService().createPrintJob();
DocFlavor flavor = DocFlavor.BYTE_ARRAY.AUTOSENSE;
Doc doc = new SimpleDoc(b, flavor, null);
PrintJobWatcher pjDone = new PrintJobWatcher(job);
job.print(doc, null);
pjDone.waitForDone();
System.out.println("Done !");
} catch (javax.print.PrintException pex) {
System.out.println("Printer Error " + pex.getMessage());
return false;
} catch(Exception e) {
e.printStackTrace();
return false;
}
return true;
}
Now Prepare a bill :)
PrinterOptions p=new PrinterOptions();
p.resetAll();
p.initialize();
p.feedBack((byte)2);
p.color(0);
p.alignCenter();
p.setText("The Dum Dum Name");
p.newLine();
p.setText("Restaurant Dining");
p.newLine();
p.addLineSeperator();
p.setText("Bling Bling");
p.newLine();
p.addLineSeperator();
p.newLine();
p.alignLeft();
p.setText("POD No \t: 2001 \tTable \t: E511");
p.newLine();
p.setText("Res Date \t: " + "01/01/1801 22:59");
p.newLine();
p.setText("Session \t: Evening Session");
p.newLine();
p.setText("Staff \t: Bum Dale");
p.newLine();
p.addLineSeperator();
p.newLine();
p.alignCenter();
p.setText(" - Some Items - ");
p.newLine();
p.alignLeft();
p.addLineSeperator();
p.newLine();
p.setText("No \tItem\t\tUnit\tQty");
p.newLine();
p.addLineSeperator();
p.setText("1" + "\t" + "Aliens Everywhere" + "\t" + "Rats" + "\t" + "500");
p.setText("1" + "\t" + "Aliens Everywhere" + "\t" + "Rats" + "\t" + "500");
p.setText("1" + "\t" + "Aliens Everywhere" + "\t" + "Rats" + "\t" + "500");
p.setText("1" + "\t" + "Aliens Everywhere" + "\t" + "Rats" + "\t" + "500");
p.setText("1" + "\t" + "Aliens Everywhere" + "\t" + "Rats" + "\t" + "500");
p.setText("1" + "\t" + "Aliens Everywhere" + "\t" + "Rats" + "\t" + "500");
p.addLineSeperator();
p.feed((byte)3);
p.finit();
feedPrinter(p.finalCommandSet().getBytes());