android 手机通过usb数据线与OTG设备通信

1.首先在AndroidManifest.xml文件中添加所需要的权限

<uses-feature android:name="android.hardware.usb.host" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />

2.然后在AndroidManifest.xml文件中的activity下添加以下代码

<activity android:name=".MainActivity">
    <intent-filter>
        <action android:name="android.intent.action.MAIN" />

        <category android:name="android.intent.category.LAUNCHER" />
    </intent-filter>
  <!--加上这句代码,手机与OTG设备连接就会启动该APP,并跳转到该activity-->
  <intent-filter>
        <action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" />
    </intent-filter>
<!--在res文件夹下面新建一个 xml的文件夹,然后新建device_filter.xml-->
<meta-data
        android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED"
        android:resource="@xml/device_filter" />
</activity>

3.新建device_filter.xml文件夹

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <usb-device
<!--这两个id由制造提供的-->
        product-id="123"
        vendor-id="1234" />
</resources>

4.在onCreate方法中初始化连接设备的一些配置,注册广播接收设备断开与连接的广播

public static final String ACTION_USB_PERMISSION = "com.test.otg.USB_PERMISSION";
@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    //获取 USB 管理器
    usbManager = (UsbManager) getSystemService(Context.USB_SERVICE);
    pendingIntent = PendingIntent.getBroadcast(this, 0, new Intent(ACTION_USB_PERMISSION), 0);
    registerBrasdcast();
    initUsb();
    initView();
}

//初始化设备

private void initUsb() {
    try { //取连接到设备上的 USB 设备集合
        HashMap<String, UsbDevice> map = usbManager.getDeviceList();
        //遍历集合取指定的 USB 设备
        for (UsbDevice device : map.values()) {
            Log.i("device", "vid:" + device.getVendorId() + "   pid:" + device.getProductId() + "   " + device.getDeviceName());
            if (1234== device.getVendorId() && 123== device.getProductId()) {
                usbDevice = device;
                if (usbManager.hasPermission(usbDevice)) {
                    usbManager.requestPermission(device, pendingIntent);
                }
                getDeviceInterface();//获取接口
                assignEndpoint(Interface2);// 分配端点
                openDevice(Interface2);//打开设备
            }
        }
        if (usbDevice == null) {
            Log.e("TAG", "没有获取到设备");
            return;
        }
    } catch (Exception e) {
        e.printStackTrace();
        toast("设备获取异常");
    }
}
// 寻找设备接口
private void getDeviceInterface() {
    if (usbDevice != null) {
        Log.i("TAG", "interfaceCounts : " + usbDevice.getInterfaceCount());
        for (int i = 0; i < usbDevice.getInterfaceCount(); i++) {
            UsbInterface intf = usbDevice.getInterface(i);
            if (i == 0) {
                Interface1 = intf; // 保存设备接口
                Log.i("TAG", "成功获得设备接口:" + Interface1.getId());
            }
            if (i == 1) {
                Interface2 = intf;
                Log.i("TAG", "成功获得设备接口:" + Interface2.getId());
            }
        }
    } else {
        Log.e("TAG", "未连接设备!");
    }
}
// 分配端点,IN /OUT,即输入输出;
private UsbEndpoint assignEndpoint(UsbInterface mInterface) {
    for (int i = 0; i < mInterface.getEndpointCount(); i++) {
        UsbEndpoint ep = mInterface.getEndpoint(i);
        if (ep.getType() == UsbConstants.USB_ENDPOINT_XFER_BULK) {
            if (ep.getDirection() == UsbConstants.USB_DIR_OUT) {
                epBulkOut = ep;
            } else {
                epBulkIn = ep;
            }
        }
        if (ep.getType() == UsbConstants.USB_ENDPOINT_XFER_CONTROL) {
            epControl = ep;
        }
        if (ep.getType() == UsbConstants.USB_ENDPOINT_XFER_INT) {
            if (ep.getDirection() == UsbConstants.USB_DIR_OUT) {
                epIntEndpointOut = ep;
            }
            if (ep.getDirection() == UsbConstants.USB_DIR_IN) {
                epIntEndpointIn = ep;
            }
        }
    }
    if (epBulkOut == null && epBulkIn == null && epControl == null
            && epIntEndpointOut == null && epIntEndpointIn == null) {
        throw new IllegalArgumentException("not endpoint is founded!");
    }
    return epIntEndpointIn;
}
// 打开设备
public void openDevice(UsbInterface mInterface) {
    if (mInterface != null) {
        UsbDeviceConnection conn = null;
        // 在open前判断是否有连接权限;对于连接权限可以静态分配,也可以动态分配权限
        if (usbManager.hasPermission(usbDevice)) {
            conn = usbManager.openDevice(usbDevice);
        } else {
            usbManager.requestPermission(usbDevice, pendingIntent);
        }
        if (conn == null) {
            return;
        }
        if (conn.claimInterface(mInterface, true)) {
            myDeviceConnection = conn;
            // 到此你的android设备已经连上otg设备
            if (myDeviceConnection != null)
                System.out.println("打开设备成功!");
        } else {
            System.out.println("无法打开连接通道。");
            conn.close();
        }
    }
}
//广播注册
private void registerBrasdcast() {
    //注册权限广播
    IntentFilter usbFilter = new IntentFilter(ACTION_USB_PERMISSION);
    //usb 插入广播
    usbFilter.addAction(UsbManager.ACTION_USB_DEVICE_ATTACHED);
    //usb 拔出广播
    usbFilter.addAction(UsbManager.ACTION_USB_DEVICE_DETACHED);
    registerReceiver(mUsbReceiver, usbFilter);
}
//广播接收
private final BroadcastReceiver mUsbReceiver = new BroadcastReceiver() {
    @Override
    public void onReceive(Context context, Intent intent) {
        Log.e("TAG", intent.getAction());
        switch (intent.getAction()) {
            case UsbManager.ACTION_USB_DEVICE_ATTACHED:
                toast("设备插入");
                initUsb();//初始化设备
                break;
            case UsbManager.ACTION_USB_DEVICE_DETACHED:
                toast("设备断开");
                break;
            case ACTION_USB_PERMISSION:
                synchronized (this) {
                    UsbDevice device = (UsbDevice) intent.getParcelableExtra(UsbManager.EXTRA_DEVICE);
                    if (intent.getBooleanExtra(UsbManager.EXTRA_PERMISSION_GRANTED, false)) {
                        if (device != null) {
                            openDevice(Interface2);
                        }
                    } else {
                        Toast.makeText(MainActivity.this, "用户拒绝了USB的权限!", Toast.LENGTH_LONG).show();
                        return;
                    }
                }
                break;
        }
    }
};

5.发送与接收数据

//发送数据
@Override
public void onClick(View v) {
    switch (v.getId()) {
if (myDeviceConnection == null) {
    toast("设备未连接或未授权!");
    return;
}
// 发送准备命令
int reto = myDeviceConnection.bulkTransfer(epBulkOut, openDate, openDate.length, 5000);
if (reto != -1) {
    Log.i("TAG", "已经发送数据" + reto);
    Message openMsg = Message.obtain();
    openMsg.what = SEND_DAT;
    mHandler.sendMessage(openMsg);
      }
   }
}
//接收数据
private Handler mHandler = new Handler() {
    @Override
    public void handleMessage(Message msg) {
        switch (msg.what) {
       case SEND_DATA:
byte[] receiverDate= new byte[20];
int rets = myDeviceConnection.bulkTransfer(epBulkIn, receiverDate, 20, 5000);
if(rets!=-1){
//处理收到的receiverDate数组,16进制的
}
    }
  }
};

6.解除广播

@Override
protected void onDestroy() {
    super.onDestroy();
    unregisterReceiver(mUsbReceiver);
}

AndroidManifest.xml的activity中没有加上这段代码,连接时总是会弹出允许设备的窗口,点默认也没有用。

<intent-filter> <action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" /> </intent-filter>

网上说可以改源码,我对源码进行修改后也不起作用,暂时不知道怎么去掉USB的权限允许窗。

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值