如何从Flutter将亚洲语言打印到热敏打印机上? [英] How to print Asian languages to a thermal printer from Flutter?

查看:354
本文介绍了如何从Flutter将亚洲语言打印到热敏打印机上?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用 Flutter 软件包 esc_pos_printer 1.5.0 来打印到热敏打印机.如果我打印拉丁字符,一切正常.我曾尝试使用多语言代码页,但是在尝试打印泰语字符时它总是失败.我需要能够使用英语,泰语,缅甸语,高棉语和越南语进行打印.此程序包中没有可用的代码页似乎不支持非拉丁美洲语言.这对我乃至其他许多人来说都是一个表演的终结者.

II向打印机发送了一个ESC命令以更改代码页,然后按预期方式打印新的代码页,其中使用泰文和拉丁文字符.但是,当我尝试打印泰语字符时,我的应用程序崩溃了.

我从调试器收到此错误:

  E/flutter(29402):[ERROR:flutter/lib/ui/ui_dart_state.cc(157)]未处理的异常:无效的参数(字符串):包含无效字符.E/flutter(29402):#0 _UnicodeSubsetEncoder.convert(dart:convert/ascii.dart:88:9)E/flutter(29402):#1 Latin1Codec.encode(dart:convert/latin1.dart:42:46) 

这是我的代码:

  void _printReceipt(BuildContext context){字符串ip ='192.168.1.100';Printer.connect(ip,port:9100).then((printer){printer.sendRaw([27,116,255]);printer.printCodeTable();printer.println('Welcome');printer.println('ยินดีต้อนรับ');printer.cut();printer.disconnect();});} 

我试图将字符串编码为字节并像这样打印

  _bytes = utf8.encode(ยินดีต้อนรับ");printer.sendRaw(_bytes); 

但是我明白了

我使用了下面建议的

解决方案

不幸的是,我认为 esc_pos_printer 软件包目前存在两个问题:

  • 它会丢失许多字符代码表,并且由于它是私有的,因此它实际上不允许您使用 PosCodeTable 构造函数传递自己的字符表,但是您可以使用手动设置字符表sendRaw

  • 您只能传递可以使用 Latin1Codec GBK编解码器,据我所知-泰语字符无法使用这些字符进行编码-这就是引发错误的原因

问题实际上归结于编码.对于泰国人来说,打印机可能希望数据以 TIS-620 的格式出现.铁๐是240,๑是241.

 //手动设置PosCodeTable-26是泰语字符代码18printer.sendRaw([27岁116,26]);printer.sendRaw([240,241]);//应该打印๐和๑ 

请记住,您确实需要设置字符代码表.我使用泰国字符代码18和数字26,因为这是我的打印机支持的字符.要找到正确的字符集代码,您可以在打印机手册中寻找 ESC t 命令-制造商通常将桌子放在这里或只是 fork& /解决方法设置字符代码表

  • 使用适当的编码器,例如中文的GBK,但它不是内置的,因为Dart仅支持少量编码,并且使用 Encoding.getByName("csTIS620") null .您可能需要自己做字符映射-我没有找到适合您需求的Dart编解码器.还有一个使用平台代码转换字符集的软件包 charset_converter .

  • 自原始答案以来的重要更新

    esc_pos_printer 现在通过 textEncoded 方法支持票证上的原始字节流.可以与 charset_converter 一起使用以打印正确的字符.

    还扩展了字符代码表,即CP1250.在 PosStyles 中将其设置为 codeTable 参数.这些通过ecs_pos_utils 项目中的打印机ID.="nofollow noreferrer">地图.

    I am using the Flutter package esc_pos_printer 1.5.0 to print to a thermal printer. It all works fine if I print Latin characters. I have tried using the mutilingual code page but it always fails when trying to print Thai characters. I need to be able to print in English, Thai, Burmese, Khmer and Vietnamese. None of the available code pages in this package appear to support non Latin Asian languages. This is a show stopper for me and possibly many others.

    II sent an ESC command to the printer to change the code page and then printed the new code page which was in Thai and Latin characters as expected. However, my app crashes when I try to print Thai characters.

    I am getting this error from the debugger:

    E/flutter (29402): [ERROR:flutter/lib/ui/ui_dart_state.cc(157)] Unhandled Exception: Invalid argument (string): Contains invalid characters.: "ยินดีต้อนรับ"
    E/flutter (29402): #0      _UnicodeSubsetEncoder.convert  (dart:convert/ascii.dart:88:9)
    E/flutter (29402): #1      Latin1Codec.encode  (dart:convert/latin1.dart:42:46)
    

    Here is my code:

    void _printReceipt(BuildContext context) {
    
      String ip = '192.168.1.100'; 
    
      Printer.connect(ip, port: 9100).then((printer) {
    
      printer.sendRaw([27, 116, 255]);
    
      printer.printCodeTable();
    
      printer.println('Welcome');
    
      printer.println('ยินดีต้อนรับ');
    
      printer.cut();
      printer.disconnect();
    }
    );
    }
    

    edit: I attempted to encode the string as bytes and print like this

    _bytes = utf8.encode("ยินดีต้อนรับ");
    
    printer.sendRaw(_bytes);
    

    but I got this

    I used the package suggested below which works well for Thai. My ESC/POS printer supports code pages 96 and 255 for Thai. 96 gets it wrong but 255 got the job done. The bottom alignment mismatch will be because printing Thai characters require 3 passes and this string contains no bottom pass characters.

    解决方案

    Unfortunetely, I think there are two issues with the esc_pos_printer package at this moment:

    • it miss many character code tables and it doesn't really allow you to pass your own using PosCodeTable constuctor since it's private, but you can set character table manually by using sendRaw

    • you can pass only characters that can be encoded using Latin1Codec or GBK codec since only these are supported, to my knowledge - Thai characters can't be encoded using these - this why the error is thrown

    The problem really comes down to encoding. For Thai, printers will probably expect the data to come in format of TIS-620. Fe. ๐ is 240, ๑ is 241.

    // Manually set PosCodeTable - 26 here is the Thai Character Code 18
    printer.sendRaw([
      27,
      116,
      26
    ]);
     
    printer.sendRaw([240, 241]); // Should print ๐ and ๑
    

    Remember that you do need to set the character code table. I used Thai Character Code 18 with number 26, because that is what my printer supports. To find right charset codes you may look for ESC t command in your printer manual - manufacturers usually put table there or just browse the internet.

    So how do we fix it?

    1. We can fork&fix/workaround setting character code tables

    2. Use proper encoder, like GBK for Chinese, but it is not built-in since Dart support only handful amount of encodings and using Encoding.getByName("csTIS620") will get you null. You may need to do character mapping yourself - I didn't found codec for Dart that would suit your needs. There is also a package charset_converter that uses platform code to convert the charsets.

    Important updates since original answer

    esc_pos_printer now supports raw byte streams on Tickets by textEncoded method. This can be used with charset_converter to print right characters.

    Also character code tables were expanded i.e. CP1250. This is set in PosStyles as codeTable parameter. Those are mapped to printer ids in ecs_pos_utils project with this map.

    这篇关于如何从Flutter将亚洲语言打印到热敏打印机上?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

    查看全文
    登录 关闭
    扫码关注1秒登录
    发送“验证码”获取 | 15天全站免登陆