Почему все печатается в одной строке, хотя я добавляю crlfs?

Это будет напечатано (хотя все еще некрасиво) на ленточном принтере Zebra QL220 из моего приложения CE/CF, работающего на портативном устройстве Motorola MC3100:

public void PrintBarcode(string barcode, string UPC, string description, decimal listPrice)
{
    using (SerialPort serialPort = new SerialPort())
    {
        serialPort.BaudRate = 19200;
        serialPort.Handshake = Handshake.XOnXOff; 
        serialPort.DataBits = 8;
        serialPort.Parity = Parity.None;
        serialPort.StopBits = StopBits.One; // other choice is Two (see p. 14-21 in CPCL pdf)
        serialPort.PortName = "COM1:"; 

        serialPort.Open(); 

        Thread.Sleep(2500); // I don't know why this is needed, or if it really is...

        serialPort.Write("! 0 200 200 210 1\r\n");

        serialPort.Write("TEXT 4 0 30 40 Hola el Mundo\r\n"); //Bonjour le Monde --- Hola el Mundo --- Hallo die Welt
        serialPort.Write("TEXT 4 0 30 40 \r\n");

        serialPort.Write("BARCODE-TEXT 7 0 5\r\n"); 
        serialPort.Write(string.Format("BARCODE 128 1 1 50 150 10 {0}\r\n", barcode));
        serialPort.Write("TEXT 4 0 30 40\r\n");
        serialPort.Write("FORM\r\n");
        serialPort.Write("PRINT\r\n");

        serialPort.Close();
    }
}

...но все вместе, как полуманиакальные подростки в мошпите - штрих-код, напечатанный последним, на самом деле находится в самой верхней точке бумаги, а "Hola el Mundo" и то, что выглядит как "FOIPM" (как что туда попасть?!?), тоже.

Если "TEXT 4 0 30 40\r\n" — это не способ отправки CRLF, то что?

ОБНОВИТЬ

Я заметил, что у меня была опечатка в аргументах для печати штрих-кода. Этот:

    serialPort.Write(string.Format("BARCODE 128 1 1 50 150 10 {0}\r\n", barcode));

... это должно было быть так:

    serialPort.Write(string.Format("BARCODE 128 1 1 50 150 130 {0}\r\n", barcode));

... но когда я "исправил" это (изменил начальную точку по вертикали с 10 до 130), результат печати был идентичен! Простите мой французский, но при чем здесь Северная Дакота?!?

ОБНОВЛЕНИЕ 2

Неважно, как только я добавлю исправление в нужное место, оно действительно сработает (изменив «10» на «130»). Теперь я должен сделать его «умным» в том смысле, что он будет учитывать предыдущие области печати и всегда печатать последующие строки ниже начальной точки + высоты предыдущих распечаток.


person B. Clay Shannon    schedule 08.02.2013    source источник


Ответы (3)


Похоже, вы пишете CPCL прямо на принтер. Используемая вами команда TEXT включает в себя координаты x и y, а именно, «30» и «40», которые вы пишете, сообщают вашему принтеру всегда печатать каждую строку текста с координатами 30,40. Попробуйте изменить эти координаты с каждой последующей строкой текста, который вы хотите напечатать. Насколько мне известно, для CPCL нет функции «автоматического переноса», поэтому вам придется делать это вручную для каждой строки текста.

Кроме того, вы можете перевести принтер в режим построчной печати. В этом режиме принтер будет просто печатать любой полученный текст, а '\r\n' заставит принтер начать печать на следующей строке. Вы можете переключить режим построчной печати, отправив на принтер следующую команду:

! U1 setvar "device.languages" "line_print" [ЗДЕСЬ НОВЫЙ СИМВОЛ СТРОКИ]

источник: Руководство CPCL — http://www.zebra.com/content/dam/zebra/manuals/en-us/printer/cpcl-pm-en.pdf

person jason.zissman    schedule 11.02.2013
comment
Так что, если я использую режим построчной печати, последующие вызовы TEXT и BARCODE и т. д. будут просто опускать позиционные аргументы? IOW, это: serialPort.Write(TEXT 4 0 30 40 Hello die Welt\r\n\r\n); ... станет следующим: serialPort.Write(string.Format(! U1 setvar {0} {1}), device.languages, line_print)); serialPort.Write(TEXT 4 0 Привет, мир\r\n\r\n); ? - person B. Clay Shannon; 11.02.2013
comment
Не совсем — если вы отправляете команду режима построчной печати, будет напечатано абсолютно все, что вы отправляете (кроме команды выхода из режима построчной печати и некоторых других!). Итак, запись serialPort.Write(Apples: $4.99\r\n); serialPort.Write(бананы: $1,99); будет две строки текста, одна поверх другой. Это так просто. Руководство по CPCL должно содержать раздел о том, как выполнять построчную печать. - person jason.zissman; 11.02.2013
comment
Хорошо, но добавление \r\n к этим строкам Write приведет к перемещению последующих строк на следующую строку, верно? - person B. Clay Shannon; 11.02.2013
comment
Ага! В этом контексте принтер интерпретирует '\r\n' как новую строку (или вместо этого вы можете использовать System.Environment.Newline!), и последующий текст появится на следующей строке. - person jason.zissman; 11.02.2013
comment
Я использую StringBuilder для объединения всех команд, которые я собираюсь отправить на принтер; если я использую AppendLine() вместо Append(), избавит ли это от необходимости добавлять \r\n к каждой строке? - person B. Clay Shannon; 12.02.2013
comment
Я не знаком с append() и appendLine(), но звучит логично, что appendLine() будет включать в конце символ новой строки. Проверьте документацию, чтобы узнать, так ли это. Если это так, вам не нужно будет добавлять себя. Тем не менее, было бы гораздо полезнее просто проверить это самостоятельно, попробовав оба метода! - person jason.zissman; 14.02.2013

Как правило, рекомендуется использовать System.Environment.Newline.

Однако в этом случае, похоже, вам может понадобиться проверить, что ваше устройство (Zebra QL220) ожидает/требует для перевода строки.

person John    schedule 08.02.2013
comment
Но опять же, в документах говорится, что XXQT02-02-0555 — понятное имя; Если XXQT02-02-0555 — дружественное имя, мне бы не хотелось видеть, что такое недружественное имя — возможно, XXQT02-02-U-Stinkin'-Jerk-0555? - person B. Clay Shannon; 09.02.2013
comment
Когда правят генералы, происходит военный переворот. - person B. Clay Shannon; 09.02.2013

Я не знаю, как писать на принтер Zebra, но:

Я вижу коды «Начало текста» (ТЕКСТ 4 0 30 40) и «Начало штрих-кода» (ШТРИХ-КОД 128 1 1).

Должен ли быть какой-то код для «Конец текста» или «Конец штрих-кода»?

Как насчет кода для «Следующей строки»?

person jp2code    schedule 09.02.2013
comment
ТЕКСТ, за которым следуют аргументы с \r\b, является следующей строкой. Конец текста или конец штрих-кода не требуются; как отмечалось в моем последнем обновлении, теперь он работает как есть. - person B. Clay Shannon; 10.02.2013