@achyutlabsau/cordova-plugin-thermal-printer
v1.2.12
Published
Cordova Plugin for Printer Library
Readme
Cordova Thermal Printer Plugin
A modern Cordova plugin for ESC/POS thermal printers with automatic per-operation connection management and Promise-based API.
📑 Table of Contents
- Features
- Platform Support
- Requirements
- Installation
- Quick Start
- API Reference
- Error Handling
- Common Use Cases
- Example Application
- Device Discovery Examples
- Best Practices
- Troubleshooting
- Architecture
- FAQ
- Contributing
- License
🚀 Features
- Automatic Connection Management: Each operation connects, executes, and disconnects automatically
- No Manual Connection Handling: No need for connect/disconnect methods
- Promise-Based API: Modern async/await syntax
- Multi-Connection Support: USB, Bluetooth, and Network printers
- Cross-Platform: Android and iOS support
- Rich Printing Options: Text, images, barcodes, QR codes
- Batch Operations: Print multiple items in sequence
- Device Discovery: Find USB and Bluetooth printers (Android)
📱 Platform Support
| Platform | USB | Bluetooth | Network/WiFi | Serial | | -------- | --- | --------- | ------------ | ------ | | Android | ✅ | ✅ | ✅ | ✅ | | iOS | 🚧 | 🚧 | ✅ | ❌ |
🚧 = Planned/In Development
📋 Requirements
- Cordova: 9.0.0 or higher
- Android: API Level 21+ (Android 5.0+)
- iOS: iOS 11.0+
- Printer: ESC/POS compatible thermal printer
Supported Printers
This plugin works with ESC/POS compatible thermal printers from various manufacturers:
- Epson TM series (TM-T20, TM-T88, etc.)
- Star Micronics (TSP100, TSP650, etc.)
- Citizen
- Bixolon
- Generic ESC/POS printers
📦 Installation
cordova plugin add @achyutlabsau/cordova-plugin-thermal-printerPermissions
The plugin automatically requests necessary permissions:
Android:
- USB access (requested automatically when connecting to USB printer)
- Bluetooth (for Bluetooth printers)
- Location (required for Bluetooth discovery on Android)
iOS:
- Bluetooth usage description (configured in plugin.xml)
- Local Network usage description (configured in plugin.xml)
🎯 Quick Start
// 1. Create printer info object
const printer = { type: 'network', id: '192.168.1.100' };
// 2. Print anything - each operation connects and disconnects automatically
await cordova.plugins.printer.printText(printer, 'Hello World!\n');
await cordova.plugins.printer.printQRCode(printer, 'https://example.com');
await cordova.plugins.printer.cutPaper(printer);
// That's it! No need to manually connect or disconnect📖 API Reference
Method Summary
| Method | Description | Platform |
| ---------------------------------------------------------- | --------------------- | ------------ |
| printText(printerInfo, text) | Print plain text | Android, iOS |
| printFormattedText(printerInfo, text, align, attr, size) | Print formatted text | Android, iOS |
| printBase64Image(printerInfo, base64, align, width) | Print base64 image | Android, iOS |
| printBarcode(printerInfo, data, codeType) | Print barcode | Android, iOS |
| printQRCode(printerInfo, data) | Print QR code | Android, iOS |
| feedLine(printerInfo, lines) | Feed paper lines | Android, iOS |
| cutPaper(printerInfo) | Cut paper | Android, iOS |
| openCashBox(printerInfo) | Open cash drawer | Android, iOS |
| printBatch(printerInfo, items) | Print multiple items | Android, iOS |
| getUsbDevices() | Get USB devices | Android |
| getBluetoothDevices() | Get Bluetooth devices | Android |
| getPrintersAsync() | Get all devices | Android |
Printer Info Objects
All methods require a printerInfo object as the first parameter:
// Network Printer (Android & iOS)
const printer = { type: 'network', id: '192.168.1.100' };
// USB Printer (Android only)
const printer = { type: 'usb', id: '0416:5011' }; // VID:PID format
// or
const printer = { type: 'usb', id: '/dev/usb/lp0' }; // Device path format
// Bluetooth Printer (Android only)
const printer = { type: 'bluetooth', id: '12:34:56:78:9A:BC' }; // MAC addressCore Printing Methods
All methods return Promises and handle connections automatically.
Print Text
await cordova.plugins.printer.printText(printerInfo, 'Hello World!\n');Print Base64 Image
await cordova.plugins.printer.printBase64Image(
printerInfo,
base64ImageString,
1, //center=1, alignment
384 // width in pixels
);Print Barcode
// codeType values: Refer to ESC/POS barcode type constants
// Common values: 73 (Code128), 69 (EAN13), 70 (EAN8), 65 (UPC-A)
await cordova.plugins.printer.printBarcode(printerInfo, '1234567890123', 69); // EAN13Print QR Code
await cordova.plugins.printer.printQRCode(printerInfo, 'https://example.com');Print Formatted Text
// Print text with custom formatting
// alignment: 0 (left), 1 (center), 2 (right)
// attribute: Text style flags (bold, underline, etc.)
// textSize: Combined width and height multiplier
await cordova.plugins.printer.printFormattedText(
printerInfo,
'Bold Centered Text\n',
1, // center alignment
0, // attribute flags
0 // text size
);Paper Control
// Feed paper lines
await cordova.plugins.printer.feedLine(printerInfo, 3);
// Cut paper
await cordova.plugins.printer.cutPaper(printerInfo);
// Open cash drawer
await cordova.plugins.printer.openCashBox(printerInfo);Batch Operations
Print multiple items in sequence with a single printer connection:
await cordova.plugins.printer.printBatch(printerInfo, [
{ type: 'text', data: 'Receipt Header\n' },
{ type: 'formattedText', data: 'Bold Text\n', alignment: 1, attribute: 0, textSize: 0 },
{ type: 'text', data: '------------------------\n' },
{ type: 'qrcode', data: 'https://example.com' },
{ type: 'barcode', data: '123456789', codeType: 73 },
{ type: 'image', data: base64ImageString, alignment: 1, width: 384 },
{ type: 'feed', lines: 3 },
{ type: 'cut' },
{ type: 'cashbox' }, // opens cash drawer
]);Available Batch Item Types:
text- Print plain textformattedText- Print text with formattingqrcode- Print QR codebarcode- Print barcodeimage- Print base64 imagefeed- Feed paper linescut- Cut papercashbox- Open cash drawer
Device Discovery
Get USB Devices (Android only)
const usbDevices = await cordova.plugins.printer.getUsbDevices();
console.log(usbDevices);
/* Output:
[
{
id: "0416:5011", // VID:PID format - use this for printerInfo
devicePath: "/dev/bus/usb/001/002",
vendorId: 1046,
productId: 20497,
name: "Thermal Printer",
manufacturer: "Epson", // may be undefined
type: "usb"
}
]
*/Get Bluetooth Devices (Android only)
const btDevices = await cordova.plugins.printer.getBluetoothDevices();
console.log(btDevices);
/* Output:
[
{
id: "12:34:56:78:9A:BC", // MAC address - use this for printerInfo
name: "Thermal Printer",
address: "12:34:56:78:9A:BC",
deviceType: 2, // Bluetooth device type
type: "bluetooth"
}
]
*/Get All Printers (Convenience Method)
// Get both USB and Bluetooth devices in one call
const allPrinters = await cordova.plugins.printer.getPrintersAsync();
console.log(allPrinters); // Combined array of USB and Bluetooth devices
// Use returned devices directly
allPrinters.forEach((printer) => {
// printer already has correct format: { type, id, name, ... }
console.log(`${printer.type}: ${printer.name} (${printer.id})`);
});🔧 Error Handling
try {
await cordova.plugins.printer.printText(printerInfo, 'Test');
console.log('Print successful!');
} catch (error) {
console.error('Print failed:', error);
// Common error scenarios:
// - "USB permission denied by user"
// - "Failed to connect to network printer"
// - "Bluetooth connection not implemented"
// - "Unsupported printer type: xyz"
}💡 Common Use Cases
Receipt Printing
const printer = { type: 'network', id: '192.168.1.100' };
// Print a complete receipt
await cordova.plugins.printer.printBatch(printer, [
{ type: 'text', data: ' MY STORE\n' },
{ type: 'text', data: ' 123 Main Street\n' },
{ type: 'text', data: '================================\n' },
{ type: 'text', data: 'Item 1 $10.00\n' },
{ type: 'text', data: 'Item 2 $15.00\n' },
{ type: 'text', data: '================================\n' },
{ type: 'text', data: 'TOTAL: $25.00\n' },
{ type: 'qrcode', data: 'https://mystore.com/receipt/12345' },
{ type: 'feed', lines: 3 },
{ type: 'cut' },
]);Label Printing
const printer = { type: 'usb', id: '0416:5011' };
// Print a shipping label
await cordova.plugins.printer.printText(printer, 'SHIP TO:\n');
await cordova.plugins.printer.printText(printer, 'John Doe\n');
await cordova.plugins.printer.printText(printer, '123 Main St\n');
await cordova.plugins.printer.printBarcode(printer, 'TRACK123456', 73);
await cordova.plugins.printer.cutPaper(printer);Kitchen Order Printing
const printer = { type: 'bluetooth', id: '12:34:56:78:9A:BC' };
// Print kitchen order
await cordova.plugins.printer.printFormattedText(
printer,
'TABLE 5 - ORDER #123\n',
1, // center
0,
0
);
await cordova.plugins.printer.printText(printer, '2x Burger\n');
await cordova.plugins.printer.printText(printer, '1x Fries\n');
await cordova.plugins.printer.feedLine(printer, 5);
await cordova.plugins.printer.cutPaper(printer);🧪 Example Application
This plugin includes a comprehensive example app that demonstrates all features:
cd example
npm install
cordova platform add android
cordova run androidThe example app (example/www/js/printer-app.js) provides:
- Device discovery (USB/Bluetooth)
- All print operations (text, images, barcodes, QR codes)
- Paper control (feed, cut, cash drawer)
- Error handling examples
- Real-world usage patterns
🔍 Device Discovery Examples
Finding and Connecting to USB Printers
// Get available USB devices
const devices = await cordova.plugins.printer.getUsbDevices();
// Display to user for selection
devices.forEach((device, index) => {
console.log(`${index}: ${device.name} (${device.id})`);
});
// Use selected device - the device object already has the correct format
const selectedDevice = devices[0];
const printer = { type: 'usb', id: selectedDevice.id };
// Test connection - automatically connects and disconnects
await cordova.plugins.printer.printText(printer, 'Connection test\n');Auto-Discovery Network Printers
// Try common printer IP addresses
const commonIPs = ['192.168.1.100', '192.168.1.200', '192.168.0.100'];
for (const ip of commonIPs) {
try {
const printer = { type: 'network', id: ip };
await cordova.plugins.printer.printText(printer, 'Test\n');
console.log(`Found printer at: ${ip}`);
break;
} catch (error) {
console.log(`No printer at: ${ip}`);
}
}✅ Best Practices
1. Store Printer Info for Reuse
// Store printer info after discovery
const selectedPrinter = { type: 'network', id: '192.168.1.100' };
localStorage.setItem('printer', JSON.stringify(selectedPrinter));
// Reuse in future sessions
const printer = JSON.parse(localStorage.getItem('printer'));
await cordova.plugins.printer.printText(printer, 'Hello!\n');2. Always Handle Errors
async function safePrint(printer, text) {
try {
await cordova.plugins.printer.printText(printer, text);
return { success: true };
} catch (error) {
console.error('Print failed:', error);
return { success: false, error: error.message };
}
}3. Test Connection Before Printing
async function testPrinterConnection(printer) {
try {
await cordova.plugins.printer.printText(printer, '');
return true;
} catch (error) {
return false;
}
}4. Use Batch Operations for Multiple Items
// ✅ Good - Single connection, faster
await cordova.plugins.printer.printBatch(printer, [
{ type: 'text', data: 'Line 1\n' },
{ type: 'text', data: 'Line 2\n' },
{ type: 'text', data: 'Line 3\n' },
]);
// ❌ Avoid - Multiple connections, slower
await cordova.plugins.printer.printText(printer, 'Line 1\n');
await cordova.plugins.printer.printText(printer, 'Line 2\n');
await cordova.plugins.printer.printText(printer, 'Line 3\n');5. Network Printer Tips
// Use static IP addresses for reliability
const printer = { type: 'network', id: '192.168.1.100' };
// Ensure printer and device are on same network
// Configure printer with fixed IP via printer settings
// Test connectivity with ping before printing🐛 Troubleshooting
Common Issues
USB Permission Denied (Android)
// The plugin automatically requests USB permissions // If denied by user, you'll get this error try { await cordova.plugins.printer.printText(usbPrinter, 'test'); } catch (error) { if (error.includes('permission denied')) { alert('Please grant USB permission and try again'); } }Network Connection Timeout
// Ensure printer IP is correct and printer is on same network const printer = { type: 'network', id: '192.168.1.100' }; // Test with a simple ping first try { await cordova.plugins.printer.printText(printer, 'Network test\n'); } catch (error) { console.log('Check network connection and printer IP'); }iOS USB Not Supported
// USB is not supported on iOS due to platform limitations // Use network printers instead if (cordova.platformId === 'ios') { // Only use network printers on iOS const printer = { type: 'network', id: '192.168.1.100' }; }
🏗️ Architecture
The plugin uses automatic per-operation connection management:
- No Persistent Connections: Each operation connects, executes, and disconnects automatically
- No Manual Connection Management: No connect/disconnect methods needed
- Promise-Based: All methods return Promises for easy async/await usage
- Thread-Safe: Each operation uses its own connection instance
- Error Propagation: Detailed error messages for debugging
- Platform Abstraction: Same API works across Android and iOS
- USB Auto-Permissions: Automatically requests USB permissions when needed (Android)
❓ Frequently Asked Questions
Q: Do I need to manually connect to the printer?
A: No! The plugin automatically handles connections. Just call any print method with the printer info and it will connect, execute, and disconnect automatically.
Q: Can I keep a persistent connection to the printer?
A: No, the plugin uses automatic per-operation connection management. Each operation opens and closes its own connection. For multiple operations, use printBatch() for better performance.
Q: Why does my app need location permission for Bluetooth?
A: Android requires location permission for Bluetooth device discovery (not for printing, just for finding devices). This is an Android platform requirement, not a plugin limitation.
Q: How do I find my printer's IP address?
A: Check your printer's settings menu, print a test page, or look at your router's connected devices list. Most thermal printers allow you to print a network configuration page.
Q: Can I print images?
A: Yes! Use printBase64Image() with a base64-encoded image string. The plugin will convert it to printer-compatible format.
Q: Does this work with receipt printers?
A: Yes! ESC/POS thermal printers are commonly used for receipts, and this plugin is designed specifically for them.
Q: How do I print special characters or non-English text?
A: Most ESC/POS printers support UTF-8 encoding. Ensure your printer firmware supports the character set you need. Some older printers may have limited character support.
Q: Can I print to multiple printers simultaneously?
A: Yes! Each print operation is independent. You can call methods for different printers in parallel:
const printer1 = { type: 'network', id: '192.168.1.100' };
const printer2 = { type: 'usb', id: '0416:5011' };
await Promise.all([
cordova.plugins.printer.printText(printer1, 'Receipt 1\n'),
cordova.plugins.printer.printText(printer2, 'Receipt 2\n'),
]);Q: What's the difference between type: 'network' and type: 'wifi'?
A: Use 'network' - it covers both WiFi and Ethernet connections. Both terms work, but 'network' is the recommended value.
🤝 Contributing
Contributions are welcome! Please feel free to submit issues or pull requests.
📄 License
MIT License - see LICENSE file for details.
Made with ❤️ by Achyut Labs
