Термопринтер печатает только один раз после перезапуска с использованием UsbDeviceConnection android - PullRequest
0 голосов
/ 21 октября 2019

В одном приложении для Android я встроил функцию печати чеков прямо из приложения с использованием термопринтера. Я использую класс «UsbDeviceConnection» для печати квитанции.

Это не всегда работает должным образом. Например, если я распечатываю квитанцию, она печатается один раз, затем, если я отправляю печать снова, она записывает все байты в соединение с принтером, но на самом деле не печатает квитанцию.

Чтобы снова распечатать квитанцию, мне нужноперезагрузить принтер один раз. Поэтому, если я перезагружу свой термопринтер, я могу снова распечатать квитанцию.

Я использую нижеуказанный класс для печати квитанции.

public class UsbCommunicator {

    private UsbManager mUsbManager;
    private PendingIntent mPermissionIntent;
    private UsbDevice selectedUsbDevice;
    private UsbInterface selectedUsbInterface;
    private int endpointOutId;
    private int endpointInId;
    private final String ACTION_USB_PERMISSION = "com.android.example.USB_PERMISSION";

    public UsbCommunicator2(Context context) {
        // Create USB manager
        mUsbManager = (UsbManager) context.getSystemService(Context.USB_SERVICE);

        // Set USB permissions broadcaster
        mPermissionIntent = PendingIntent.getBroadcast(context, 0, new Intent(ACTION_USB_PERMISSION), 0);
        context.registerReceiver(mUsbReceiver, new IntentFilter(ACTION_USB_PERMISSION));
    }

    public ArrayList<UsbDevice> getConnectedDevices() {
        ArrayList<UsbDevice> usbDevices = new ArrayList<>();
        // Get every connected USB device and store in HashMap
        HashMap<String, UsbDevice> deviceList = mUsbManager.getDeviceList();
        Iterator<UsbDevice> deviceIterator = deviceList.values().iterator();
        // Loop through every connected USB device
        while (deviceIterator.hasNext()) {
            UsbDevice device = deviceIterator.next();
            usbDevices.add(device);
        }
        return usbDevices;
    }

    public void setDevice(UsbDevice device) {
        if (!mUsbManager.hasPermission(device))
            mUsbManager.requestPermission(device, mPermissionIntent);
        else {
            selectedUsbDevice = device;
            setDeviceInterface(device);
            setDeviceEndpoints(device);
        }
    }

    public void sendData(byte[] bytes, CommunicationListener commListener) {
        if (!deviceSelected() || !hasPermission()) return;
        UsbEndpoint outputEndpoint = selectedUsbInterface.getEndpoint(endpointOutId);

        new CommunicatorTask(commListener, outputEndpoint, bytes).execute();
    }

    public boolean deviceSelected() {
        return selectedUsbDevice != null ? true : false;
    }

    public boolean hasPermission() {
        return deviceSelected() && mUsbManager.hasPermission(selectedUsbDevice);
    }

    private void setDeviceInterface(UsbDevice device) {
        // Get the device interface, this is known to be 0 for the targetted Star and Sanei devices, but can vary for other devices
        selectedUsbInterface = device.getInterface(0);
    }

    private void setDeviceEndpoints(UsbDevice device) {
        if (selectedUsbInterface == null) return;
        // Loop through every end point on the interface to find the right end points
        for (int i = 0; i < selectedUsbInterface.getEndpointCount(); i++) {
            UsbEndpoint endpoint = selectedUsbInterface.getEndpoint(i);
            if (endpoint.getDirection() == UsbConstants.USB_DIR_OUT)
                endpointOutId = i;
            else if (endpoint.getDirection() == UsbConstants.USB_DIR_IN)
                endpointInId = i;
        }
    }

    private final BroadcastReceiver mUsbReceiver = new BroadcastReceiver() {

        public void onReceive(Context context, Intent intent) {
            String action = intent.getAction();
            if (ACTION_USB_PERMISSION.equals(action)) {
                synchronized (this) {
                    UsbDevice device = intent.getParcelableExtra(UsbManager.EXTRA_DEVICE);
                    // Device permission was granted
                    if (intent.getBooleanExtra(UsbManager.EXTRA_PERMISSION_GRANTED, false)) {
                        if (device != null) {
                            selectedUsbDevice = device;
                            setDeviceInterface(device);
                            setDeviceEndpoints(device);
                        }
                    }
                }
            }
        }
    };

    private class CommunicatorTask extends AsyncTask<Void, Void, Integer> {

        private CommunicationListener commListener;
        private UsbEndpoint outputEndpoint;
        private byte[] bytes;
        private UsbDeviceConnection connection;

        public CommunicatorTask(CommunicationListener commListener, UsbEndpoint outputEndpoint, byte[] bytes) {
            this.commListener = commListener;
            this.outputEndpoint = outputEndpoint;
            this.bytes = bytes;

            connection = mUsbManager.openDevice(selectedUsbDevice);
            connection.claimInterface(selectedUsbInterface, true);
        }

        protected Integer doInBackground(Void... unused) {
            int bytesWritten = 0;
            while (bytesWritten < bytes.length) {
                bytesWritten += connection.bulkTransfer(outputEndpoint, bytes, bytesWritten, bytes.length - bytesWritten, 0);
            }
            return bytesWritten;
        }

        protected void onPostExecute(Integer bytesTransferred) {
            connection.close();
            commListener.onComplete(bytesTransferred);
        }
    }
}

Ниже приведен код в моем файле активности.

UsbCommunicator usbComm = new UsbCommunicator(context);

ArrayList<UsbDevice> connectedDevices = usbComm.getConnectedDevices();

if(connectedDevices.size() == 0) {
    Toast.makeText(context, "No USB Printer Detected", Toast.LENGTH_SHORT).show();
    return;
}

UsbDevice device = connectedDevices.get(0);
usbComm.setDevice(device);
Bytes[] bytes = createSampleReceipt(imgPath); << This method will convert Image to Bytes array

usbComm.sendData(bytes, new CommunicationListener(){

    @Override
    public void onComplete(int bytesTransferred) {
        Toast.makeText(context, "Printer Success", Toast.LENGTH_SHORT).show();
    }
});

В этом случае печать работает только один раз, а затем для печати другой квитанции, мне нужно перезапустить термопринтер. В реальном сценарии он должен отправлять все распечатки согласно запросу и не требует перезагрузки принтера.

...