viernes, 18 de mayo de 2012

Configurar tipos de fuentes y estilos en impresoras matriciales Epson

En cualquier sistema empresarial actual aún es normal que se necesite imprimir comprobantes pre-impresos con impresoras de tipo matriz de punto, cuya calidad de impresión puede ser personalizada ajustando los tipos de fuentes y los estilos de impresión.

Como en muchos casos las impresoras utilizadas para este tipo de aplicaciones son de la marca Epson, principalmente LX-300/300+/300+II, en este artículo se documenta el procedimiento a seguir para configurar los estilos y fuentes de impresión desde la consola de comandos Linux, y desde un servidor de aplicaciones OAS (Oracle Application Server).


Desde la consola

Para realizar este tipo de configuraciones sin la intervención del usuario, las mismas pueden ser enviadas remotamente a las impresoras desde la consola de comandos del sistema operativo. Estos comandos son secuencias de caracteres de control que las impresoras reconocen y diferencian del contenido de impresión, para posteriormente interpretarlos y modificar su configuración a medida que los va recibiendo.

En entornos de tipo Unix-like, las secuencias de caracteres de control deben ser enviadas a las impresoras en formato hexadecimal. Básicamente se envía una cadena de caracteres a la entrada estándar del comando lp con el comando echo, el parámetro -d del comando lp permite definir cual será la impresora en la que se enviará la impresión. A continuación se verán algunos ejemplos:
  1. Para configurar el estilo de impresión de texto a Negrita tenemos que enviar el siguiente comando a una impresora matricial registrada en el sistema operativo:
    testsrv:~ # echo -en '\x1B\x45' | lp -d lpgabriel
    
    El primer código hexadecimal \x1B es un comando de escape que le indica a la impresora que se prepare para recibir una configuración específica, que en este caso es el comando hexadecimal siguiente \x45 que aplica el estilo de letra negrita.
    OBS: Con la tubería (pipe, |) el comando echo pasa a la impresora los comandos de configuración en formato hexadecimal. Los argumentos e y n (-en) del comando echo activan la interpretación de las barras invertidas y remueven el salto de nueva línea (del comando echo) respectivamente.
  2. También podemos indicarle a la impresora para que realice un salto de línea de la siguiente manera:
    testsrv:~ # echo -en '\x1B\x0A' | lp -d lpgabriel
    
  3. Si queremos cambiar el tipo letra que por defecto suele ser Draft o Draft Condensed a Roman o Saint Serif, primero debemos habilitar el uso de fuentes NLQ (Near Letter Quality) con el siguiente comando:
    testsrv:~ # echo -en '\x1B\x78\x01' | lp -d lpgabriel
    
    Luego indicarle el tipo de fuente NLQ a usar, para Roman se usa el siguiente comando:
    testsrv:~ # echo -en '\x1B\x6B\x00' | lp -d lpgabriel
    
    Y para Saint Serif el siguiente:
    testsrv:~ # echo -en '\x1B\x6B\x01' | lp -d lpgabriel
    
  4. Si queremos volver a configurar la impresora para Draft y Draft Condensed tenemos que desactivar el uso de fuentes NLQ de la siguiente forma:
    testsrv:~ # echo -en '\x1B\x78\x00' | lp -d lpgabriel
    
Estos son solo algunos ejemplos de comandos que permiten configurar las impresoras matriciales Epson, otros comandos y sus funciones se encuentran detallados en los documentos enlazados al final del artículo.


Mediante Oracle Report Builder y Oracle Application Server (OAS)

Como suelo trabajar con Report Builder de Oracle, se presentó la necesidad de imprimir comprobantes pre-impresos con una fuente distinta y mucho más oscura, para lo cual la fuente Roman con el estilo Negrita era la opción recomendada.

Para entrar en contexto, el escenario que me tocó es el siguiente:
  • Un servidor de reportes Oracle Report Server, que es un módulo del OAS (Oracle Application Server) instalado en un servidor Linux.
  • Las impresoras físicas de matriz de punto conectadas a computadoras de escritorio (Windows o Linux) y compartidas en red.
  • Las impresoras remotas montadas en el servidor OAS mediante Samba (smb), y configuradas como impresoras de texto plano.
Con este escenario los comandos o secuencias de control se tienen que enviar desde el servidor de reportes en Linux a las impresoras remotas.

La solución recomendada para estos casos es agregar las secuencias de caracteres de control a un archivo utilizado para configurar la salida de impresión en el servidor de reportes. Estos archivos llevan la extensión .prt y existen varios de ellos dependiendo de la configuración de salida que se necesite. Para que los reportes utilicen la definición de un archivo .prt, se tiene que asignar el nombre del archivo en el parámetro de sistema DESFORMAT durante el periodo de diseño del reporte en Oracle Report Builder, o bien incluirlo en tiempo de ejecución en la lista de parámetros del procedimiento que llama al reporte en un formulario diseñado con Oracle Forms Builder.

Ahora, ¿donde se encuentran los archivos de definición .prt? Pues eso depende de la instalación del servidor de reportes, lo que si es seguro es que los archivos tienen que encontrarse dentro de los directorios especificados en el PATH del servidor para que cuando se ejecute el reporte lo encuentre sin problemas y pueda aplicar el formato de impresión. En el caso del IAS 9i (Internet Application Server de Oracle) los archivos se encuentran en el directorio /ias/6iserver/report60/admin/printer/, y en el OAS 10g (Oracle Application Server) se encuentran en el directorio /oracle/app/oracle/product/midtier/reports/printers/.

A continuación se presenta el contenido de ejemplo de un archivo .prt:
printer "comprobantes"

height   24
width    80

before report  esc hex(30)  esc hex(35)  esc hex(21)hex(03)  esc hex(43)hex(18)  esc hex(50)  esc hex(45)  esc hex(78)hex(01)  esc hex(6B)hex(00)

after page

return        ""
linefeed      control(J)
Con las directivas height y width se indica al servicio de impresión del OAS (porque el OAS tiene sus propias definiciones de impresoras .ppd similares a cups) la cantidad de líneas y columnas respectivamente que tendrá cada página. Luego, seguido de la directiva before report van todos los comandos hexadecimales que permiten configurar la impresora matricial Epson antes de imprimir el contenido del reporte. A continuación se aclara cada conjunto de comandos del ejemplo:
  • esc hex(30): Le indica a la impresora que utilice un interlineado de 8 líneas por pulgada (1/8), ya que por defecto estas impresoras vienen configuradas en 1/6, o lo que sería lo mismo, 6 líneas por pulgada.
  • esc hex(35): Cancela el estilo cursiva si es que estuviese activado.
  • esc hex(21)hex(03): Aplica un estilo general de impresión donde el valor 03 corresponde a la suma de los códigos indicadores 1 y 2 que definen una configuración de 12 cpi e impresión proporcional de letras respectivamente. En realidad bien podría haber sido el valor en hexadecimal 02, ya que en vez de 12 cpi que tiene el indicador 1 se podría usar el indicador cero (0) de 10 cpi para sumarlo al indicador 2 de impresión proporcional de letras, ya que más adelante se configura nuevamente la impresora a 10 cpi (esc hex(50)).
  • esc hex(43)hex(18): Fija la longitud de la página en 24 líneas (18 hex == 24 dec).
  • esc hex(50): Configura a la impresora en 10 cpi (characters per inch).
  • esc hex(45): Esta secuencia de control configura la impresora para que el estilo de la fuente sea negrita.
  • esc hex(78)hex(01): Configura la impresora para que use letras de tipo NLQ (Near Letter Quality) en reemplazo de letras de tipo borrador como Draft y Draft Condensed.
  • esc hex(6B)hex(00): Esta secuencia sirve para seleccionar la letra Roman del tipo NLQ (Near Letter Quality).
Todos estos comandos llevan el carácter de escape esc, que antecede a todos los códigos hexadecimales. Para mayor información acerca de estos y otros caracteres de escape les recomiendo consultar los documentos enlazados al final de este artículo.

Para el caso en que el servidor OAS y el runtime de ejecución de los reportes estuviese instalado en un sistema operativo Windows, la disposición de las directivas del archivo .prt difieren un poco con las utilizadas en Linux. El contenido del archivo anterior de ejemplo quedaría como sigue:
printer "comprobantes"
height   24
width    80
before report
esc hex(30)
esc hex(35)
esc hex(21)hex(03)
esc hex(43)hex(18)
esc hex(50)
esc hex(45)
esc hex(78)hex(01)
esc hex(6B)hex(00)
after page
return        ""
linefeed      control(J)

Documentos útiles

Los comandos para configurar las impresoras matriciales Epson mencionados en este artículo y varios otros más se encuentran documentos en los siguientes enlaces, de los cuales ya se ha hablado en otra entrada que pueden encontrar entre los enlaces del resumen de guías.

34 comentarios :

  1. Hola Gabriel, primero que todo gracias por el artículo. Estamos haciendo una migración de Forms/Reports 6i a Forms/Reports 11g. Nos encontramos con la situación que los tiquetes en impresoras POS que antes se imprimían bien, ahora son ilegibles. El problema es que no es en modo caracter, sino en modo bitmap. ¿Te has encontrado ante esta situación? De ser así, ¿Sabes cómo resolverlo?
    gracias

    ResponderEliminar
    Respuestas
    1. Hola, la verdad que a mi aún no se me presentó algo parecido, ya sea porque nunca he probado enviar impresiones en modo bitmap, (siempre he utilizado la opción MODE=Default), o bien porque sigo utilizan el Forms y Reports 10g.

      Las impresoras que usan son de la marca Epson? modelo TMU tal vez? es raro que no te funcione, son como las impresoras Epson LX-300, y que por cierto, ya has probado enviar la impresión a una LX-300?

      Saludos.

      Eliminar
  2. Amigo gabril tengo una Impresora Epson TM-U220A y necesisto imprimir un Ticket de esta Manera: pero quiero Fuente: Draft o sualquiera que yo le ordene, aqui te envio mi codigo gracias:
    Sub Imprimir()
    Dim X As Long
    If MsgBox("Desea imprimir Ticket?", 324, VbTitulo) = vbYes Then

    Documento = Me.TxtSigla.Text & Format(Me.TxtSerie.Text, "000") & "-" & Format(TxtNumero.Text, "00000000")

    With Me

    Printer.Font.Size = 8
    Printer.Font.Bold = True
    Printer.Font.Name = "A11"
    Printer.Print Tab(0); VbEmpresa
    Printer.Print Tab(20); Documento
    Printer.Print Tab(10); Format(Date, "dddd, d mmm, aaaa")
    Printer.Font.Bold = False
    Printer.Print Tab(5); ""
    Printer.Print Tab(5); ""
    Printer.Print Tab(0); "Cliente : " & Me.LabelNombres.Caption
    Printer.Print Tab(0); "RUC : " & Me.TxtRuc.Text
    Printer.Print Tab(5); ""
    Printer.Print Tab(0); "-------------------------------------------------------------------"
    Printer.Print Tab(0); "Cant."; Tab(8); "Detalle"; Tab(30); "Pre.U."; Tab(42); "Importe"
    Printer.Print Tab(0); "-------------------------------------------------------------------"
    Printer.Print Tab(5); ""
    For X = 1 To Me.FlexFac.Rows - 1
    Printer.Print Tab(0); .FlexFac.TextMatrix(X, 3); Tab(5); .FlexFac.TextMatrix(X, 2); Tab(35 - Len(Format(.FlexFac.TextMatrix(X, 4), "###,##0.00"))); Format(.FlexFac.TextMatrix(X, 4), "###,##0.00"); Tab(50 - Len(Format(.FlexFac.TextMatrix(X, 6), "###,##0.00"))); Format(.FlexFac.TextMatrix(X, 6), "###,##0.00")
    Next
    Printer.Print Tab(0); "-------------------------------------------------------------------"
    Printer.Print Tab(20); "SubTotal : "; Tab(50 - Len(Format(.LabelST.Caption, "###,##0.00"))); Format(.LabelST.Caption, "###,##0.00")
    Printer.Print Tab(20); "Descuento : "; Tab(50 - Len(Format(.LabelDescuento.Caption, "###,##0.00"))); Format(.LabelDescuento.Caption, "###,##0.00")
    Printer.Print Tab(20); "Flete : "; Tab(50 - Len(Format(.LabelFlete.Caption, "###,##0.00"))); Format(.LabelFlete.Caption, "###,##0.00")
    Printer.Print Tab(20); "Igv (18%) : "; Tab(50 - Len(Format(.LabelIGV.Caption, "###,##0.00"))); Format(.LabelIGV.Caption, "###,##0.00")
    Printer.Print Tab(20); "Total : "; Tab(50 - Len(Format(.LabelTotal.Caption, "###,##0.00"))); Format(.LabelTotal.Caption, "###,##0.00")
    Printer.Print Tab(5); ""
    Printer.Print Tab(0); "Gracias por su Compra!!!"
    Printer.Print Tab(5); ""
    Printer.Font.Size = 6
    Printer.Print Tab(5); "Usuario : " & FormMenu.LabelUser.Caption
    Printer.Print Tab(5); "Impreso : " & Date & " " & Time
    Printer.EndDoc
    End With

    End If




    'Printer.Print Tab(69); "SUBTOTAL :"; Tab(99 - Len(Format(mon1, "###,###,##0"))); Format(mon1, "###,###,##0")
    End Sub

    ResponderEliminar
    Respuestas
    1. Hola, no estoy muy al tanto de como será para hacerlo con VB, lo que supongo que hay que hacer es tratar de enviar los comandos esc/p requeridos antes de iniciar la impresión del ticket.

      En el artículo yo envío las secuencias de configuración desde la propia consola de Linux, lo mismo supongo que se podrá hacer desde el CMD de Windows y por supuesto enviarlos desde tu programa, quizás en formato hexadecimal o ascii, pero siempre cuidando que sea texto sin formato, sin retornos de carro, etc.

      Eliminar
  3. Amigo Grabiel te agradesco mucho pero te cuento que solucione mi problema y quiero compartirlo con ustedes, yo trabajo con Visual Basic 6.0, Sql server 2008 y Crystal Report 2008, tanto me di cuenta que Cree mi Ticket en Crystal Report y solo le di la fuente "FONTA11" instalada de la maquina Tickitera a todo el ticket y cuando imprimi salio justo como yo queria.. de antemano gracias!!! jose WILLIANS NAVARRO YOVERA - CATACAOS- PIURA PERU- E-MAIL: estrategiasmarwill@hotmail.com

    ResponderEliminar
    Respuestas
    1. Hola José, que suerte que lo hayas solucionado.. Saludos y éxitos!

      Eliminar
  4. Estimados, tengo un problema y no se como solicionarlo, tengo una epson fx-890 y cuando imprimo desde word todo sale bine pero cualquier documento tipo PDF que envio, la calidad de impresion es muy mala, es ilegible, no se si les ha pasado y como resolverlo, de antemano gracias por la ayuda

    ResponderEliminar
    Respuestas
    1. Hola, como es una impresora matriz de punto no creo que sea adecuado enviarle archivos pdf, porque dudo que interprete correctamente el lenguaje PostScript. Creo que lo más adecuado sería enviarle texto plano, como por ejemplo el contenido de un txt, o estás necesitando imprimir algún borde o detalle como una imagen? Saludos.

      Eliminar
  5. Hola amigo Gabril necesito ayuda por favor me podrias decir como covertir un campo Texto a Chekbox en Cristal Report 2008.... Gracias Saludos!!! Jose willians

    ResponderEliminar
    Respuestas
    1. Lo lamento, no manejo nada de Cristal Report? Saludos!

      Eliminar
  6. hola tengo una impresora tm-u325pd y cuando imprimo desde el oas no utiliza el driver de la validadora, porque podria ser? gracias

    ResponderEliminar
    Respuestas
    1. Hola Antonio, a que te refieres con el "driver de la validadora"? con la configuración de la impresora realizada desde el sistema operativo?

      Eliminar
  7. Asi es Gabriel, o sea, tengo instalado el driver de la impresora en mi maquina local, lo que necesito es utilizar la validadora de la impresora, pero el oas me arroja la impresión como "Receipt" y yo necesito como "validation". En forma local imprimiendo directamente desde el report me funciona pero al levantar en el sistema que tengo el oas arroja directamente la impresión al lpt1 sin tomar en cuenta el driver de la validadora.

    ResponderEliminar
    Respuestas
    1. Ya, tu servidor del OAS en que sistema operativo está instalador? supongo que tu impresora está compartida en Windows y la misma se encuentra montada en el servidor (Linux) como impresora remota Samba ..

      Eliminar
  8. Hola, y para que me imprima tildes(áéíóú) y eñes (Ññ) cual es el comando. Muchas gracias.

    ResponderEliminar
    Respuestas
    1. Hola Alex, sinceramente no sabría decirte, que impresora matricial tienes?

      Eliminar
  9. hola, tengo 2 entornos de trabajo windows y linux, servidor de reportes oracle. Mi problema es el siguiente: tengo una impresora epson lq-590 compartida por windwos al cual mando impresiones en papel continuo para cheques(4 por hoja), al mandar el report generado en windows sin problemas, el tema esta al mandar el mismo reporte desde linux a la impresora compartida de windows, las letras salen borrosas y luego del 3er cheque se junta con el 4to, el report se genera en pdf. Tendrias alguna soluciona?
    muchas gracias

    ResponderEliminar
    Respuestas
    1. Hola José Coronel, es probable que tu Oracle Report server en Linux esté enviando la impresión como archivo Postscript, y no como texto plano como debe ser. Para que el Reports te envié como texto plano debes configurar adecuadamente los parámetros de sistema de tu reporte, configuración que por cierto en estos momentos no me acuerdo.

      Saludos!

      Eliminar
  10. Buenas, estoy imprimiendo una boleta continua( diseñado un crystal reports), en una epson Lx300++ me imprime muy bien todo.
    Pero el mismo diseño de boleta continua en una epson FX 890 me imprime los caracteres muy pegados uno del otro. He intentado cambiar los cpp, el tipo de letra de la impresora pero nada.
    Si alguien sabe como tratar con la epson FX890, quizas haya movido alguna configuracion, mientras cuadradaba el tamaño de hoja o necesito configurar algo mas en la impresora.
    De antemano gracias

    ResponderEliminar
    Respuestas
    1. Hola Anónimo, como estás, será que tu impresora no está configurada con el tipo de letra condensada?

      Eliminar
  11. Hola amigo, existe alguna solucion para poder imprimir bien un pdf en una matricial fx-890

    ResponderEliminar
    Respuestas
    1. Hola Henry, yo la verdad que no lo se, no le podes enviar solo texto?

      Eliminar
  12. hola amigos . tengo un problema con la epson LX300+ no hay forma de poder cambiar la fuente a condensada , he probado lo de los 3 seg el boton pause y apretar font con los diferentes parpadeos y a pagar pero sin resultados. alguien puede orientarme . gracias anticipadas.

    ResponderEliminar
    Respuestas
    1. Hola Anónimo, te consulto, la impresión que mandas no te está configurando de vuelta la impresora? Saludos!

      Eliminar
  13. Hola, estoy imprimiendo un reporte en formato matricial este es el código del prt :
    printer "ReciboMatri"
    height 30
    width 160
    code "bold on" esc "E"
    code "bold off" esc "F"
    code "underline on" esc "-1"
    code "underline off" esc "-0"
    code "bold underline on" esc "E" esc "-1"
    code "bold underline off" esc "F" esc "-0"
    code "900" esc "W1"
    code "901" esc "W0"
    before report esc "M" esc hex(43)hex(1B) esc " "
    between pages control(L)
    return control(M)
    linefeed control(J)
    Lo que pasa es que imprime todo bien pero cuando acaba la impresión de la pagina, salta un intervalo y se posiciona en la segunda hoja, tengo que darle al botón Tear Off/Bin de la impresora matricial Epson FX-890 para que regrese ese salto y poder imprimir correctamente.
    Agradeceré su ayuda.

    ResponderEliminar
    Respuestas
    1. Hola Julio, envías directamente tu impresión a una Impresora de tu Windows no?, si en Windows has configurado tu impresora matricial es probable que la cola de impresión de Windows le agregue un salto de hoja al finalizar la impresión, prueba ir en Impresoras, abre la ventana de propiedades de tu impresora y en la la pestaña Opciones avanzadas le marcás la opción Imprimir directamente en la impresora. Espero que te sea de ayuda, saludos...

      Eliminar
    2. No creo que sea eso porque ya probé... el problema es en la codificación del prt

      Eliminar
    3. Julio, un comentario acerca sobre tu archivo .prt, al comienzo has definido una altura de 30 y luego con la directiva hex(43)hex(1B) esc le indicas que es solo de 27 (hex(1B) = 27).
      Por otro lado, ¿has probado sin las directivas between pages control(L) y return control(M)?

      Prueba con algo similar al ejemplo que puse en el artículo, así bien cortito, y luego ve agregándole más cosas..

      Saludos..

      Eliminar
    4. Hola Gabriel, encontre la solucion el problema a sido de la impresora... y del servidor donde estaba trabajando.. hice la prueba poniendo mis fuentes y prt en otro servidor y cambiando de impresora matricial y Funciono, el codigo prt esta bien.. Muchas Gracias por la Ayuda.

      Eliminar
    5. Genial Julio, que suerte que haya funcionado..

      Eliminar
  14. Hola, Tengo un ambiente linux, agregué la impresora mediante cups (epson fx 890) y estoy trabajando con Weblogic 11, necesito imprimir en formularios pre impresos pero no logro que la impresora obedezca el archivo prt. Qué puedo hacer??
    Además, requiero usar la compresión para que los reportes quepan dentro de la hoja, cuál sería la instrucción que lo activa??

    Agradezco su ayuda!

    Saludos

    ResponderEliminar
    Respuestas
    1. Hola Hazel, ahora recién leo tu comentario, prueba configurar tu impresora matricial en cups como tipo Genérico - Raw, así lo uso yo con Weblogic 11g para las impresoras LX300 y para las impresoras térmicas Zebra, y funciona.. De esta forma uno se asegura que los comandos ESC/P u otros lleguen a la impresora correctamente..

      Saludos!!

      Eliminar
  15. hola amigo tengo una impresora LX-350 que por error toque la tecla de menú(SET)
    y ahora me imprime símbolos ,números,letras chinas, cuamdo enbio un documento cualquiera
    ayuda por favor gracias

    ResponderEliminar
  16. Hola. Tengo una pregunta que tipo de fuente y que tamano viene configurada la impresora de matriz de punto epson lx350 originalmente de fabrica, ya que por error se coloco otra fuente y otro tamaño y al imprimir el comprobante sale en desorden y el formato sale en otras dimensiones, en cambio en la configuracion predeterminada de la epson si imprimia correctamente. Gracias por la ayuda

    ResponderEliminar