Printing a pdf file on a thermal printer - android

I getting issue, printing through bluetooth on thermal printer from pdf file become text view.
Print Pdf file via Bluetooth Printer Android I was tried these example but didn't what I expected.
this is my current code
code file source:
String checkout = "checkout";
String fpath = Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) +"/"+ checkout + ".pdf";
code to printing
FileInputStream fis = new FileInputStream(file);
ByteArrayOutputStream bos = new ByteArrayOutputStream();
byte[] buf = new byte[1024];
try {
for (int readNum; (readNum = fis.read(buf)) != -1;) {
bos.write(buf, 0, readNum);
System.out.println("read " + readNum + " bytes,");
}
} catch (IOException ex) {
System.out.println("ERROR!");
}
byte[] bytesPDF = bos.toByteArray();
byte[] printformat = { 27, 33, 0 }; //try adding this print format
mService.write(printformat);
mService.write(bytesPDF);
I hope able to print pdf file by thermal bluetooth printer. Please help me. Thankyou.

The issue is very clear. As we can see that the printed receipt has formatting syntaxes with it. Which is used to format text and images in a PDF file. So, the printer through which you are trying to print doesn't support printing a PDF file. So, if possible you should provide the file in a compatible format such as a text file.
To know more about formatting text in a Bluetooth printer, you can have a look at this post here. Let me know whether this solves your problem or not.

The way how Thermal printer works is
Open socket connection to printer
Send the encoded data that the printer understands
Close the connection
So, the question here boils down to what's the format of the data to be sent so that the printer is able to understand it and print accordingly. It depends on the manufacturer of the Printer. The encodings are either well documented, packed into an SDK/driver for use or are open source standard encoding for ESC/POS generic printers.
At the end, what you need to do to print a PDF file is -
Convert PDF file to Bitmap[] of pages.
Encode the pages one by one by the command for printing bitmap as provided by the manufacturer.
Pass this encoded string data to the printer.
For Example, do look at the generic ESC/POS implementation in the following GitHub Repo
https://github.com/DantSu/ESCPOS-ThermalPrinter-Android
PrinterTextParserImg.bitmapToHexadecimalString()

Related

Printing a receipt to a file

I can print a receipt (byte[] printer format) via a thermal printer, like this :
// Print a receipt
OutputStream outputStream = mPrinterSocket.getOutputStream();
for (byte[] packet : content)
outputStream.write(packet);
outputStream.flush();
But I can not manage to save a receipt (byte[] printer format) into a file (pdf or image).
I tried :
// Save a receipt
try (OutputStream outputStream = new FileOutputStream(filePath)) {
for (byte[] packet : content) {
outputStream.write(packet);
outputStream.flush();
}
} catch (Exception exception) {
exception.printStackTrace();
}
But it returned a corrupted file, containing:
䀛琛ᬐšℝ䴑ਊℝ䴀‬੍੍ㄊ⼵㔰ㄯ‹ㄱ㈺‱†††††慔汢⁥਱䔛ਁ′潂獩潳獮†††††††††††ᬊE‱潃慣†††††††††††⸲〲ᬊE‱慆瑮⁡††††††††††⸲〲ⴊⴭⴭⴭⴭⴭⴭⴭⴭⴭⴭⴭⴭⴭⴭⴭਭ䔛吁呏䱁†††††††††䔠剕㐠㐮ਰਊ䔛䴀牥楣‬⃠楢湥⁴ਡਊਊᴊV
Is the process to "print a byte[] to file" different from "save a byte[] to file"? For example, I use the character {0x1b, 0x45, 0x01} to put a text in bold, is this a problem? I would like to avoid reformatting everything or using an external library.
I'd wrap the FileOutputStream into a BufferedOutputStream, instead of using a plain FOS. When reading from or writing to a file it is always a good practice to use a buffer.
Also, you don't need to flush() after each packet, just outside of the loop - as in your first example. This also improves performance.
You can use the itext library for android to create PDF file and save it. For more details Read Here

Converting Image To PCL And Printing Via Bluetooth

Problem:
Using an Android device, without internet / network connection, I have to print images to a bluetooth enabled printer.
Be aware that this is the business case — I cannot use Google Cloud Print, nor can I use PrinterShare or anything else like that. The data generated by the app is medical in nature and must be kept confidential and within the app.
What I’ve accomplished:
Generating PCL data (text only, no images) to send to a bluetooth connection that the printer can process and output.
What I’ve tried:
Generating PCL data (image) using the Android ImageMagick port (found here: https://github.com/paulasiimwe/Android-ImageMagick) and sending the generated PCL data to the bluetooth connection.
Result:
Gibberish, but gibberish that appears to be the right dimensions of the image I am trying to print.
==============
My hypothesis is that there’s something slightly off in my implementation of the conversion, but I’m not sure what it is.
Sample Code:
NOTE: this is proof of concept work and captures an image from the Assets dir, makes it available, and then converts it.
// Attempt to get image file from Assets folder
AssetManager assetManager = context.getAssets();
InputStream istr = assetManager.open("test.jpg");
Bitmap bitmap = BitmapFactory.decodeStream(istr);
// Access External Storage Directory and save file
String root = Environment.getExternalStorageDirectory().toString();
File tempDirectory = new File(root + "/temp");
tempDirectory.mkdirs();
String fileName = "test.jpg";
File file = new File (tempDirectory, fileName);
try {
FileOutputStream out = new FileOutputStream(file);
bitmap.compress(Bitmap.CompressFormat.JPEG, 90, out);
out.flush();
out.close();
} catch (Exception exception) {
// Exception found
}
// Capture file of recently saved image, convert to PCL
try{
ImageInfo originalInfo = new ImageInfo(Environment.getExternalStorageDirectory().getAbsolutePath() + "/temp/test.jpg");
MagickImage mImage = new MagickImage(originalInfo);
String newInfoPath = Environment.getExternalStorageDirectory().getAbsolutePath() + "/temp/test.pcl";
mImage.setFileName(newInfoPath);
mImage.setImageFormat("pcl");
ImageInfo newInfo = new ImageInfo(newInfoPath);
mImage.writeImage(newInfo);
} catch (MagickException exception) {
// Exception found
}
I then retrieve the PCL file and send it to the bluetooth connection (using another method that works using standard PCL files), but as mentioned the output is gibberish.
I feel like I’m missing something simple, but I’m just not seeing it.
Also, I am seeing the following in LogCat that may / may not be related, but I haven't been able to find any information about resolving this nor can I determine if it's anything more than a warning.
V/Magick: ThrowException
V/Magick: severity: 395
V/Magick: reason: UnableToOpenConfigureFile `policy.xml' # warning/configure.c/GetConfigureOptions/589
V/Magick: Attempting to read from file /storage/emulated/0/temp/test.jpg
V/Magick: ThrowException
V/Magick: severity: 395
V/Magick: reason: UnableToOpenConfigureFile `magic.xml' # warning/configure.c/GetConfigureOptions/589
V/Magick: OpenPixelCache()
V/Magick: - cache_info->columns: 144
V/Magick: - cache_info->rows: 144
V/Magick: - cache_info->offset: 0
V/Magick: - cache_info->length: 165888
V/Magick: - length: 207360
V/Magick: - create memory pixel cache
V/Magick: ReadImage completed
Does anyone have any experience with this or can anyone point me in the right direction?

REST Server for uploading and downloading documents

I wrote an android application that part of it is to handle upload and download documents. Currently I am using the Microsoft Azure server to save the files on.
The way I am currently doing it is by turning the files to a string and saving it that way on the Azure server:
ByteArrayOutputStream baos = new ByteArrayOutputStream();
FileInputStream fis;
try {
fis = new FileInputStream(new File(Uridata.getPath()));
byte[] buf = new byte[1024];
int n;
while (-1 != (n = fis.read(buf)))
baos.write(buf, 0, n);
} catch (Exception e) {
e.printStackTrace();
}
byte[] bbytes = baos.toByteArray();
item.setStringFile(Base64.encodeToString(bbytes, Base64.URL_SAFE));
item.setName(Uridata.getLastPathSegment());
where item is my class that saves the string representation and the name of the file and is being loaded to the Azure, Uridata is an Uri instance of the file chosen.
I have one main problem with this solution and it is the limit on the file size.
I am searching for a good server to use instead of the Azure (maybe a RESET one) and if there is a better way to save files of all kinds (pdf, word...).
I will also want in the future to use the same data in a web interface
Does anybody have any suggestions on how to do it?
Thanks in advance!
To start, you don't have to transform the file into a string, you can just save it as a file. You have the possibility of losing data by continuing to do that. See: How do I save a stream to a file in C#?
If you're looking for another service to save files, then you should look into Azure Blob Storage. It will allow you to upload as much data as you want to a storage service for arbitrary files. See for example:
https://azure.microsoft.com/en-us/documentation/articles/storage-dotnet-how-to-use-blobs/

Android Read and Write File to Serial Port at Specific Frequency

Greetings. I have been using Serial PORT API to Transmit Data to Serial Port and the following code to read and write file to serial port.
File file = new File(musicpath + "file.txt");
StringBuilder text = new StringBuilder();
try {
BufferedReader br = new BufferedReader(new FileReader(file));
String line="";
int c,counter=0;
while ((c = br.read()) != -1) {
String s = new StringBuilder().append("").append((char)c).toString();
MainActivity.sendDataChar(s);
}
}
catch (IOException e) {
//You'll need to add proper error handling here
}
I have been transmitting 8 BIT MONO WAVE FILES # 22Khz from SD CARD using RS485 and I do have hardware to playback the transmitted data using DAC. (BOTH TRANSMITTER and RECEIVER uses ARM7 - LPC2148).
Now my idea is to have the 8 BIT WAVE FILE stored in SDCARD of Android Device and transmit the same at specified frequency using timer.
I wanted to know how to do this. I tried the above method but I do understand that the transmission frequency does not match as I needed. (PORT OPENED AT 230400 baud rate).
With the above code, a 155 KB File should take approximately 6-7 seconds to finish up the transmission character by character. But it really takes about 15-20 seconds and I dont have the audio output at the receiver end. Just the noise.
Kindly advise me and give some ideas on how to do it in realtime just like the way I managed to do it in ARM7.
Thanks a Lot

Use IPP(Internet Printing Protocol) or LPR(Line printer Remote) to print file in android

My requirement is to print a file from an android device without using any cloud based service.
I have been able to achieve it using "Raw" print protocol i.e by simply sending the file to printer's IP address at Port 9100. Here is the code snippet for that:
client = new Socket(ip,port); //Port is 9100
byte[] mybytearray = new byte[(int) file.length()]; //create a byte array to file
fileInputStream = new FileInputStream(file);
bufferedInputStream = new BufferedInputStream(fileInputStream);
bufferedInputStream.read(mybytearray, 0, mybytearray.length); //read the file
outputStream = client.getOutputStream();
outputStream.write(mybytearray, 0, mybytearray.length); //write file to the output stream byte by byte
outputStream.flush();
bufferedInputStream.close();
outputStream.close();
The problem with "Raw" printing protocol is that there is no way to get the status back from the printer.
So, I recently read about IPP and LDR using which we can get the status back from printer.
I have tried to find a way to implement them using android but had no success. I have already went through this answer but had no success in finding my solution.
It will be really helpful if someone can guide me on how to implement IPP or LDR in android.
Thanks in advance!
General usage of IPP:
Once a print job has been submitted the printer returns a job-id
Use the Get-Job-Attributes-Operation in order to get the current job-state
Wait until the attribute job-state equals to 9 (means 'completed')
There are other final job-states you should check for: aborted or canceled
For prototyping you could use the ipptool (native for desktop usage):
# ipptool -t -d job=482 ipp://192.168.2.113/ipp job.ipp
{
OPERATION Get-Job-Attributes
GROUP operation-attributes-tag
ATTR charset attributes-charset utf-8
ATTR language attributes-natural-language en
ATTR uri printer-uri $uri
ATTR integer job-id $job
}
Update 5/2020
I have published a kotlin implementation of the ipp protocol.
https://github.com/gmuth/ipp-client-kotlin
Once submitted you can wait for the print job to terminate: job.waitForTermination()

Categories

Resources