6

I'm trying to print out raw ascii data to a thermal printer. I do this by using this code example: http://support.microsoft.com/kb/322091 but my printer prints always only one character and this not until I press the form feed button. If I print something with notepad the printer will do a form feed automatically but without printing any text.

The printer is connected via usb over a lpt2usb adapter and Windows 7 uses the "Generic -> Generic / Text Only" driver.

Anyone knows what is going wrong? How is it possible to print some words and do some form feeds? Are there some control characters I have to send? And if yes: How do I send them?

Edit 14.04.2010 21:51

My code (C#) looks like this:

PrinterSettings s =  new PrinterSettings();
s.PrinterName = "Generic / Text Only";

RawPrinterHelper.SendStringToPrinter(s.PrinterName, "Test");

This code will return a "T" after I pressed the form feed button (This litte black button here: swissmania.ch/images/935-151.jpg - sorry, not enough reputation for two hyperlinks)

Edit 15.04.2010 16:56

I'm using now the code form here: c-sharpcorner.com/UploadFile/johnodonell/PrintingDirectlytothePrinter11222005001207AM/PrintingDirectlytothePrinter.aspx

I modified it a bit that I can use the following code:

byte[] toSend;
// 10 = line feed
// 13 carriage return/form feed
toSend = new byte[1] { 13 };
PrintDirect.WritePrinter(lhPrinter, toSend, toSend.Length, ref pcWritten);

Running this code has the same effekt like pressing the form feed button, it works fine!

But code like this still does not work:

byte[] toSend;
// 10 = line feed
// 13 carriage return/form feed
toSend = new byte[2] { 66, 67 };
PrintDirect.WritePrinter(lhPrinter, toSend, toSend.Length, ref pcWritten);

This will print out just a "B" but I expect "BC" and after running any code I have to reconnect the USB cable to make it work agian. Any ideas?

Thomas Kekeisen
  • 4,355
  • 4
  • 35
  • 54
  • What printer are you using, and what text are you sending? Most printers use control languages; you send them commands, they do not print out whatever you send. – Dour High Arch Apr 14 '10 at 16:55
  • I use this one here, but I could not find any documentation about it until now: http://www.swissmania.ch/A662078/Miniatur_Thermodrucker_CELECTRONIC_Card_Star.html – Thomas Kekeisen Apr 14 '10 at 19:56
  • You will have to get technical support from the manufacturer; only they know what control language that printer was designed to accept. – Dour High Arch Apr 14 '10 at 20:35

2 Answers2

8

Quick step by step solution

Because code was not provided, I make it work with help of provided links, and here is the code:

Code

using System;
using System.Runtime.InteropServices;
using System.Windows;

[StructLayout(LayoutKind.Sequential)]
public struct DOCINFO {
    [MarshalAs(UnmanagedType.LPWStr)]
    public string pDocName;
    [MarshalAs(UnmanagedType.LPWStr)] 
    public string pOutputFile;
    [MarshalAs(UnmanagedType.LPWStr)] 
    public string pDataType;
}

public class PrintDirect {
    [DllImport("winspool.drv", CharSet = CharSet.Unicode, ExactSpelling = false, CallingConvention = CallingConvention.StdCall)]
    public static extern long OpenPrinter(string pPrinterName, ref IntPtr phPrinter, int pDefault);

    [DllImport("winspool.drv", CharSet = CharSet.Unicode, ExactSpelling = false, CallingConvention = CallingConvention.StdCall)]
    public static extern long StartDocPrinter(IntPtr hPrinter, int Level, ref DOCINFO pDocInfo);

    [DllImport("winspool.drv", CharSet = CharSet.Unicode, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
    public static extern long StartPagePrinter(IntPtr hPrinter);

    [DllImport("winspool.drv", CharSet = CharSet.Ansi, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
    public static extern long WritePrinter(IntPtr hPrinter, string data, int buf, ref int pcWritten);

    [DllImport("winspool.drv", CharSet = CharSet.Unicode, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
    public static extern long EndPagePrinter(IntPtr hPrinter);

    [DllImport("winspool.drv", CharSet = CharSet.Unicode, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
    public static extern long EndDocPrinter(IntPtr hPrinter);

    [DllImport("winspool.drv", CharSet = CharSet.Unicode, ExactSpelling = true, CallingConvention = CallingConvention.StdCall)]
    public static extern long ClosePrinter(IntPtr hPrinter);
}

private void Print(String printerAddress, String text, String documentName) {
    IntPtr printer = new IntPtr();

    // A pointer to a value that receives the number of bytes of data that were written to the printer.
    int pcWritten = 0;

    DOCINFO docInfo = new DOCINFO();
    docInfo.pDocName = documentName;
    docInfo.pDataType = "RAW";

    PrintDirect.OpenPrinter(printerAddress, ref printer, 0);
    PrintDirect.StartDocPrinter(printer, 1, ref docInfo);
    PrintDirect.StartPagePrinter(printer);

    try {
    PrintDirect.WritePrinter(printer, text, text.Length, ref pcWritten);
    } catch (Exception e) {
        Console.WriteLine(e.Message);
    }

    PrintDirect.EndPagePrinter(printer);
    PrintDirect.EndDocPrinter(printer);
    PrintDirect.ClosePrinter(printer);
}

Usage

String printerAddress = "\\\\ComputerName\\PrinterName";
String documentName = "My document";
String documentText = "This is an example of printing directly to a printer.";

this.Print(printerAddress, documentText, documentName);

Sources:

yurislav
  • 1,119
  • 12
  • 17
  • Your link is dead! and your code isn't copy pasted correctly! you are missing `MarshalAs` and `public` in your `struct` – AaA Mar 09 '18 at 10:54
  • No, link was targetin official microsoft site article, that no longer exists. Here is alternative arcile: https://support.microsoft.com/en-us/help/138594/howto-send-raw-data-to-a-printer-by-using-the-win32-api – yurislav Mar 10 '18 at 11:50
  • Would you edit your answer and include correct link, please? – AaA Mar 12 '18 at 01:29
  • Here is a C# console application to send RAW print jobs to printers https://github.com/chrisvesper/PrintRaw – Chris Vesper Aug 17 '20 at 18:45
6

Okay, the reason for all that stuff is just the fact that I use an adapter because my computer does not has an old lpt port. I copied my application to an old computer running windows xp and everything works fine.

Now I have to hope that some other lpt2usb adaters I bought do their work correctly.

Edit 20.04.2010

With another lpt2usb adapter everything works fine now. If anyone is intersted in all the code I am using now, please contact me or comment here.

Thomas Kekeisen
  • 4,355
  • 4
  • 35
  • 54
  • 1
    Ill love to see How You did print to LPT using C#, Thanks in advance – adopilot Jun 09 '10 at 14:15
  • I am working on project which needs to print to Thermal printer. Can you blog your experience with the same? – Abhijeet Nagre Aug 05 '15 at 18:14
  • 1
    I´m printing to Thermal printers using this Nuget https://www.nuget.org/packages/RawPrint/ Source Code https://github.com/frogmorecs/RawPrint – cdiazal Mar 20 '18 at 17:17
  • @ThomasKekeisen , if you don't you don't mind then I may ask for the code "lpt2usb" – roy Jul 08 '22 at 07:50