Flutter热敏打印机控制插件esc_pos_gen的使用
Flutter热敏打印机控制插件esc_pos_gen的使用
esc_pos_gen
是一个用于生成热敏打印机 ESC/POS 命令的库。该库提供了声明式的风格来创建打印内容。
特性
- 📝 声明式风格(就像创建 Flutter 小部件一样)
- 📰 表格打印(使用
PosRow
) - 😎 文本样式:
- 大小、对齐方式、加粗、反向、下划线、不同字体、旋转 90°
- 📸 打印图像
- 🔠 打印条形码:
- UPC-A, UPC-E, JAN13 (EAN13), JAN8 (EAN8), CODE39, ITF (Interleaved 2 of 5), CODABAR (NW-7), CODE128
- ✂️ 纸张切割(部分切割、全切割)
- 🚗 发出蜂鸣声(不同持续时间)
- 📃 纸张进纸、回退
注意:您的打印机可能不支持所有上述功能(如某些样式、部分或全纸张切割、条形码等)。
创建打印内容
简单的带样式的打印内容
List<int> generatePaper() {
final CapabilityProfile profile = await CapabilityProfile.load();
final Generator generator = Generator(
PaperSize.mm58,
profile,
);
final List<PosComponent> components = [
const PosText.center('My Store'),
const PosSeparator(),
PosList.builder(
count: 20,
builder: (int i) {
return PosList(
[
PosRow.leftRightText(
leftText: 'Product $i',
rightText: 'US\$ $i',
),
PosRow.leftRightText(
leftText: '1 x US\$ $i',
leftTextStyles: const PosStyles.defaults(
fontType: PosFontType.fontB,
),
rightText: 'US\$ $i',
rightTextStyles: const PosStyles.defaults(
align: PosAlign.right,
fontType: PosFontType.fontB,
),
),
],
);
},
),
const PosSeparator(),
PosBarcode.code128('{A12345'.split('')),
const PosSeparator(),
const PosFeed(1),
const PosCut(),
];
final Paper paper = Paper(
generator: generator,
components: components,
);
return paper.bytes;
}
使用组件委托的简单打印内容
class StoreSocialMediaLinks extends PosDelegate {
const StoreSocialMediaLinks();
PosComponent build(Generator generator) {
return PosList([
PosRow.leftRightText(
leftText: 'Instagram',
leftTextStyles: const PosStyles.defaults(
fontType: PosFontType.fontB,
),
rightText: '@iandi.s',
rightTextStyles: const PosStyles.defaults(
align: PosAlign.right,
fontType: PosFontType.fontB,
),
),
PosRow.leftRightText(
leftText: 'Github',
leftTextStyles: const PosStyles.defaults(
fontType: PosFontType.fontB,
),
rightText: 'github.com/iandi.s',
rightTextStyles: const PosStyles.defaults(
align: PosAlign.right,
fontType: PosFontType.fontB,
),
),
]);
}
}
List<int> generatePaper() {
final CapabilityProfile profile = await CapabilityProfile.load();
final Generator generator = Generator(
PaperSize.mm58,
profile,
);
final List<PosComponent> components = [
const PosText.center('My Social Media Links'),
const PosSeparator(),
const PosComponent.delegate(StoreSocialMediaLinks()),
const PosSeparator(),
const PosFeed(1),
const PosCut(),
];
final Paper paper = Paper(
generator: generator,
components: components,
);
return paper.bytes;
}
打印表格行
PosRow([
PosColumn(
text: 'col3',
width: 3,
styles: PosStyles(
align: PosAlign.center,
underline: true,
),
),
PosColumn(
text: 'col6',
width: 6,
styles: PosStyles(
align: PosAlign.center,
underline: true,
),
),
PosColumn(
text: 'col3',
width: 3,
styles: PosStyles(
align: PosAlign.center,
underline: true,
),
),
]);
打印图像
此包实现了三种 ESC/POS 函数:
ESC *
- 列格式打印GS v 0
- 位图格式打印(已过时)GS ( L
- 位图格式打印
注意,您的打印机可能只支持其中的一些函数。
import 'dart:io';
import 'package:esc_pos_gen/esc_pos_gen.dart';
import 'package:image/image.dart';
final ByteData data = await rootBundle.load('assets/logo.png');
final Uint8List bytes = data.buffer.asUint8List();
final Image image = decodeImage(bytes);
// 使用 `ESC *`
PosImage(image: image);
// 使用 `GS v 0` (已过时)
PosImage.raster(image: image);
// 使用 `GS ( L`
PosImage.raster(
image: image,
imageFn: PosImageFn.graphics,
);
打印条形码
final List<int> barData = [1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 4];
PosBarcode(Barcode.upcA(barData));
// 或者
// PosBarcode.upcA(barData);
打印二维码
使用原生 ESC/POS 命令:
PosQRCode('example.com');
如果您的打印机不支持原生命令,则可以将二维码作为图像打印。首先添加依赖项:
dependencies:
qr_flutter: ^4.0.0
path_provider: ^2.0.0
然后使用以下代码:
String qrData = "google.com";
const double qrSize = 200;
try {
final uiImg = await QrPainter(
data: qrData,
version: QrVersions.auto,
gapless: false,
).toImageData(qrSize);
final dir = await getTemporaryDirectory();
final pathName = '${dir.path}/qr_tmp.png';
final qrFile = File(pathName);
final imgFile = await qrFile.writeAsBytes(uiImg.buffer.asUint8List());
final img = decodeImage(imgFile.readAsBytesSync());
return PosImage(image: img);
} catch (e) {
print(e);
}
使用代码表
不同的打印机支持不同的代码表集。一些打印机型号在 CapabilityProfile
类中定义。因此,如果您想更改默认代码表,重要的是选择正确的配置文件:
// Xprinter XP-N160I
final profile = await CapabilityProfile.load('XP-N160I');
final generator = Generator(PaperSize.mm80, profile);
bytes += generator.setGlobalCodeTable('CP1252');
所有可用的配置文件可以通过调用获取:
final profiles = await CapabilityProfile.getAvailableProfiles();
更多关于Flutter热敏打印机控制插件esc_pos_gen的使用的实战教程也可以访问 https://www.itying.com/category-92-b0.html
更多关于Flutter热敏打印机控制插件esc_pos_gen的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
当然,以下是一个关于如何使用Flutter中的esc_pos_gen
插件来控制热敏打印机的示例代码。esc_pos_gen
是一个Flutter插件,用于通过ESC/POS命令集控制热敏打印机。这个插件支持蓝牙、USB和网络连接的打印机。
首先,确保你已经在pubspec.yaml
文件中添加了esc_pos_gen
依赖:
dependencies:
flutter:
sdk: flutter
esc_pos_gen: ^x.y.z # 替换为最新版本号
然后,运行flutter pub get
来安装依赖。
接下来是一个简单的示例代码,展示如何通过蓝牙连接打印机并发送打印指令:
import 'package:flutter/material.dart';
import 'package:esc_pos_bluetooth/esc_pos_bluetooth.dart';
import 'package:esc_pos_printer/esc_pos_printer.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(
title: Text('ESC/POS Printer Example'),
),
body: Center(
child: PrintButton(),
),
),
);
}
}
class PrintButton extends StatefulWidget {
@override
_PrintButtonState createState() => _PrintButtonState();
}
class _PrintButtonState extends State<PrintButton> {
EscPosBluetooth? _bluetooth;
EscPosPrinter? _printer;
@override
void initState() {
super.initState();
_bluetooth = EscPosBluetooth();
_initPrinter();
}
Future<void> _initPrinter() async {
// 扫描蓝牙设备(实际项目中应添加用户选择设备的逻辑)
List<EscPosDevice> devices = await _bluetooth!.scanDevices();
if (devices.isNotEmpty) {
EscPosDevice device = devices.first; // 选择第一个设备作为示例
_printer = await EscPosPrinter.connectBluetooth(device.address, device.name);
} else {
print("No devices found");
}
}
Future<void> _printReceipt() async {
if (_printer != null) {
await _printer!.printText('Hello, ESC/POS!\n');
await _printer!.cutPaper();
} else {
print("Printer not initialized");
}
}
@override
Widget build(BuildContext context) {
return ElevatedButton(
onPressed: _printReceipt,
child: Text('Print Receipt'),
);
}
@override
void dispose() {
_printer?.disconnect();
_bluetooth?.close();
super.dispose();
}
}
注意事项:
- 权限处理:在实际应用中,需要处理蓝牙权限和设备扫描请求。
- 设备选择:上述示例中直接选择了扫描到的第一个设备。在实际应用中,应添加用户选择设备的界面。
- 错误处理:示例代码中没有添加详细的错误处理逻辑,实际项目中应添加适当的错误处理。
- 打印指令:
esc_pos_gen
插件支持多种ESC/POS指令,可以根据需要发送不同的指令来实现复杂的打印功能。
蓝牙权限配置(Android):
在AndroidManifest.xml
中添加蓝牙权限:
<uses-permission android:name="android.permission.BLUETOOTH"/>
<uses-permission android:name="android.permission.BLUETOOTH_ADMIN"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
并在build.gradle
(app级别)中添加对AndroidX
蓝牙库的依赖:
dependencies {
implementation 'androidx.bluetooth:bluetooth-common:1.0.5'
implementation 'androidx.bluetooth:bluetooth-le:1.1.0'
}
蓝牙权限请求(Flutter代码):
在实际应用中,你需要请求蓝牙权限,特别是在Android 6.0及以上版本。可以使用permission_handler
插件来处理权限请求。
希望这个示例代码能帮助你理解如何使用esc_pos_gen
插件来控制热敏打印机。如果有更多具体需求或问题,欢迎继续提问!