Printing with Windows Phone

Last week I hosted a session at an event named WPReborn, organized by the Community DotNetLombardia at the Microsoft headquarters in Milan.

As the name of the event say, all the sessions try to clarify all the news coming with WP8 bat also many aspect that usually you don’t find around.

My speech was about the Enterprise Application on WP8.

I specifically develop a demo of an app for the paying park management with relative ticket emission.

Every day we see similar app around the city, but (till now) no one is based on Windows Phone.

I’ll try to share my experience about the connection and use of a little thermal ticket printer to my device and use it to print.

Let’s start from the printer: I’ve used a Custom MY Printer Bluetooth.

They recently announced the support for Windows Phone 8 and in the next week they will publish a little SDK to interface and use the printer.

At the time of preparing my presentation I don’t have the SDK, so I’ve used a more “oldstyle” approach to the programmation.

Connection and communication

The connection with the printer use the Bluetooth channel that (obviously) need to be active on the phone and a relation established between the devices.

Now from the App we can look for the available (and connected) Bluetooth device with the following code:

1: PeerFinder.AlternateIdentities[ "Bluetooth:PAIRED" ] = "" ; 2: try 3: { 4: IReadOnlyList<PeerInformation> devices = 5: await PeerFinder.FindAllPeersAsync();

The obtained list can be searched for the device name (in my case I look for the string “MY Printer” in the device name list.

Now we can effectively open the communication channel with the device:

1: this .btsocket = new StreamSocket(); 2: try 3: { 4: await this .btsocket.ConnectAsync 5: (hname, "{00001101-0000-1000-8000-00805F9B34FB}" ); 6: } 7: ... 8: if ( this .btsocket != null ) 9: { 10: this .txData = new DataWriter 11: ( this .btsocket.OutputStream); 12: this .rxData = new DataReader 13: ( this .btsocket.InputStream) 14: }

And then create a DataWriter and a DataReader that we will use for write or read on the printer.

Let’s Print

And now come the “enjoyable” part, now we start to send strings to the printer that will be impress on the little thermal paper strip.

We need to consider that the printer work in ESC/POS emulation, in order to change the size or typology of a char, of its height, width or print it in negative we need to send some control character before the string to print.

For example, to print in negative is necessary to send the Hex sequence “1D” “42” “01” followed by the string to print, then we will send the sequence “1D” “42” “00” that will disable this print mode:

1: txData.WriteBytes(Cmd_ALTCMD); 2: txData.WriteBytes(Cmd_Inverse); 3: txData.WriteBytes(Cmd_ON); 4: txData.WriteString( "| Enterprise APP on WP8 |" ); 5: txData.WriteBytes(Cmd_CommandLF); 6: txData.WriteBytes(Cmd_ALTCMD); 7: txData.WriteBytes(Cmd_Inverse); 8: txData.WriteBytes(Cmd_OFF); 9: 10: await (IAsyncOperation< uint >) 11: txData.StoreAsync();

where the various “Cmd…” are defined in the following:

1: byte [] Cmd_CommandLF = new byte [] { 10 }; 2: byte [] Cmd_ESC = new byte [] { 27 }; 3: byte [] Cmd_ALTCMD = new byte [] { 29 }; 4: byte [] Cmd_Enlarged = new byte [] { 69 }; 5: byte [] Cmd_ON = new byte [] { 1 }; 6: byte [] Cmd_OFF = new byte [] { 0 }; 7: byte [] Cmd_Inverse = new byte [] { 66 }; 8: byte [] Cmd_ModoStampa = new byte [] { 33 }; 9: byte [] Cmd_D_LargALT = new byte [] { 48 }; 10: byte [] Cmd_D_LargALT_font2 = new byte [] { 49 }; 11: byte [] Cmd_D_Larg = new byte [] { 32 }; 12: byte [] Cmd_D_Alte = new byte [] { 16 };

Calling “StoreAsync()” get the stream of data previously placed on the stream and sent it (asynchronously) to the printer.

This programming approach get us back many year, when programming a report mean come crazy between control code and line feed; an unfair daily war.

A similar approach, but more complicated apply for the graphics printing, but in this case we need to divide the image in “stripe” of bit that represent the image (a bit representation of it) that will be sent to the printer in packet with a specific syntax.

In these days I receive info from the producer of the printer about the availability of the complete SDK where we can print a bitmap starting from the image file without any conversion to do.

UPDATE: the producer (CUSTOM) had released a demo application on the store. The app permit to test textual and graphic layout on the printer. You can download it free at the following link.