Android中通过USB连接来控制硬件设备
现在好多设备都有USB接口,在Android系统的手机或者开发板上可以实现通过USB来控制设备。一般手机上没有USB接口,需要使用OTG功能的转接线扩展出USB母口;一般Android开发板上带有USB口就可以直接使用了。
USB连接中需要知道对应USB设备的vendorId(设备厂商Id)和productId(设备产品Id),这两个id主要是用于连接和过滤设备。那么下面我们就先来看下拿到设备怎样找设备的vendorId和productId:
(1)先将设备通过USB口连接到电脑上;
(2)我的电脑->管理->设备管理器->找到链接的usb设备->右键属性->详细信息->硬件ID->其中的VID就是厂商id、PID是产品id。如下图所示:
这个ID是16进制的,需要转换成10进制的在 xml---device_filter.xml文件里配置。
在res目录下新建文件夹,名字是xml,然后再xml文件夹里新建device_filter.xml文件
这里的每一个usb-device对应一个usb设备;如果应用需要对多个设备使用,这里可以添加多个usb-device对应的usb设备的vendor-id和product-id;如果应用可以对同一个厂商的所有设备使用,这里可以只写vendor-id(个人是这么理解的)。
前面的准备工作做好了就可以进行下面的开发了:
(1)在AndroidManifest.xml中申明USB权限:
android:name="android.hardware.usb.host" android:required="true" /> (2)在AndroidManifest.xml中对应Activity中添加下面内容: android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" android:resource="@xml/usb_xml"/> 通过设备的vendorId(设备厂商Id)和productId(设备产品Id)找到设备 /** * 找到自定设备 */ public UsbDevice getUsbDevice(int vendorId, int productId) { //1)创建usbManager if (usbManager == null) usbManager = (UsbManager) mContext.getSystemService(Context.USB_SERVICE); //2)获取到所有设备 选择出满足的设备 HashMap Iterator while (deviceIterator.hasNext()) { UsbDevice device = deviceIterator.next(); Log.e(TAG, "vendorID--" + device.getVendorId() + "ProductId--" + device.getProductId()); if (device.getVendorId() == vendorId && device.getProductId() == productId) { return device; // 获取USBDevice } } statue = USBContent.usb_find_this_fail; return null; } 查找所有连接的USB设备,与上面的通过id查找设备 两者根据实际情况来选用。 /** * 查找本机所有的USB设备 */ public List //1)创建usbManager if (usbManager == null) usbManager = (UsbManager) mContext.getSystemService(Context.USB_SERVICE); //2)获取到所有设备 选择出满足的设备 HashMap Iterator //创建返回数据 List while (deviceIterator.hasNext()) { UsbDevice device = deviceIterator.next(); Log.e(TAG, "vendorID--" + device.getVendorId() + "ProductId--" + device.getProductId()); lists.add(device); } return lists; } 连接USB设备 /** * 根据指定的vendorId和productId连接USB设备 * * @param vendorId 产商id * @param productId 产品id */ public int connection(int vendorId, int productId) { usbDevice = getUsbDevice(vendorId, productId); //3)查找设备接口 if (usbDevice == null) { Log.e(TAG, "未找到目标设备,请确保供应商ID" + vendorId + "和产品ID" + productId + "是否配置正确"); return statue; } UsbInterface usbInterface = null; for (int i = 0; i < usbDevice.getInterfaceCount(); i++) { //一个设备上面一般只有一个接口,有两个端点,分别接受和发送数据 usbInterface = usbDevice.getInterface(i); Log.e("USBHelper","usbInterface.getEndpointCount()="+usbInterface.getEndpointCount()); break; } //4)获取usb设备的通信通道endpoint for (int i = 0; i < usbInterface.getEndpointCount(); i++) { UsbEndpoint ep = usbInterface.getEndpoint(i); switch (ep.getType()) { case UsbConstants.USB_ENDPOINT_XFER_BULK://USB端口传输 if (UsbConstants.USB_DIR_OUT == ep.getDirection()) {//输出 epBulkOut = ep; Log.e(TAG, "获取发送数据的端点"); } else { epBulkIn = ep; Log.e(TAG, "获取接收数据的端点"); } break; case UsbConstants.USB_ENDPOINT_XFER_CONTROL://控制端点 epControl = ep; Log.e(TAG, "find the ControlEndPoint:" + "index:" + i + "," + epControl.getEndpointNumber()); break; case UsbConstants.USB_ENDPOINT_XFER_INT://中断端点 if (ep.getDirection() == UsbConstants.USB_DIR_OUT) {//输出 epIntEndpointOut = ep; Log.e(TAG, "find the InterruptEndpointOut:" + "index:" + i + "," + epIntEndpointOut.getEndpointNumber()); } if (ep.getDirection() == UsbConstants.USB_DIR_IN) { epIntEndpointIn = ep; Log.e(TAG, "find the InterruptEndpointIn:" + "index:" + i + "," + epIntEndpointIn.getEndpointNumber()); } break; default: break; } } //5)打开conn连接通道 if (usbManager.hasPermission(usbDevice)) { //有权限,那么打开 conn = usbManager.openDevice(usbDevice); } else {//没有权限 usbManager.requestPermission(usbDevice, intent);// 先去获取权限 if (usbManager.hasPermission(usbDevice)) { // 权限获取成功 conn = usbManager.openDevice(usbDevice); } else { Log.e(TAG, "USB授权失败"); statue = USBContent.usb_permission_fail; } } if (null == conn) { Log.e(TAG, "不能连接到设备"); statue = USBContent.usb_open_fail; return statue; } //打开设备 if (conn.claimInterface(usbInterface, true)) { if (conn != null)// 到此你的android设备已经连上设备 Log.e(TAG, "open设备成功!"); final String mySerial = conn.getSerial(); Log.e(TAG, "设备serial number:" + mySerial); statue = USBContent.usb_ok; } else { Log.e(TAG, "无法打开连接通道。"); statue = USBContent.usb_passway_fail; conn.close(); } return statue; } 发送数据 /** * 通过USB发送数据 */ public void sendData(byte[] buffer) { if (conn == null || epBulkOut == null) return; int res = conn.bulkTransfer(epBulkOut, buffer, buffer.length, 1000); Log.e(TAG, "res="+res); if (res >= 0) { //0 或者正数表示成功 Log.e(TAG, "发送成功"); statue = USBContent.usb_permission_ok; } else { Log.e(TAG, "发送失败的"); statue = USBContent.usb_permission_fail; } } 使用完关闭USB连接 /** * 关闭USB连接 */ public void close() { if (conn != null) { //关闭USB设备 conn.close(); conn = null; } if (mContext != null && broadcastReceiver != null) { mContext.unregisterReceiver(broadcastReceiver); } } 到这里USB的连接、通过USB向硬件设备发送数据就完成了,在此做下记录,方便以后参考使用。大家如果看到了此文章,如果发现哪里有问题欢迎指正。(本人也是刚刚接触USB通信,对USB通信了解有限,上面这个是用到了亲自试验的记录一下) 感谢参考文章:https://blog.csdn.net/u013057253/article/details/82725585 还有一篇USB协议基本知识文章个人感觉写的也不错,对刚接触USB的会有帮助,附上个链接https://blog.csdn.net/u010142953/article/details/82627591