实验目的:
STM32通过USB转串口向Android Device持续发送数据,并让其显示在Android Device的Editview界面上
manifest.xml
- <?xml version="1.0" encoding="utf-8"?>
 - <manifest xmlns:android="http://schemas.android.com/apk/res/android"
 - package="com.example.dai.usb_test">
 - <uses-feature android:name="android.hardware.usb.host"></uses-feature>
 - <application
 - android:allowBackup="true"
 - android:icon="@mipmap/ic_launcher"
 - android:label="@string/app_name"
 - android:supportsRtl="true"
 - android:theme="@style/AppTheme">
 - <activity
 - android:name=".UsbTestActivity"
 - android:label="@string/app_name"
 - android:theme="@style/AppTheme.NoActionBar">
 - <intent-filter>
 - <action android:name="android.intent.action.MAIN" />
 - <category android:name="android.intent.category.LAUNCHER" />
 - </intent-filter>
 - <intent-filter>
 - <action android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED" />
 - </intent-filter>
 - <meta-data android:name="android.hardware.usb.action.USB_DEVICE_ATTACHED"
 - android:resource="@xml/usb_device_filter" />
 - </activity>
 - </application>
 - </manifest><strong>
 - </strong>
 
xml/usb_device_filter.xml:
- <?xml version="1.0" encoding="utf-8"?>
 - <resources>
 - <usb-device vendor-id="6790" product-id="29987" />
 - </resources>
 
注:vendor-id和product-id都为十进制数值;
USB_Admin:
- package com.example.dai.usb_test;
 - import android.content.BroadcastReceiver;
 - import android.content.Context;
 - import android.content.Intent;
 - import android.hardware.usb.UsbDevice;
 - import android.hardware.usb.UsbDeviceConnection;
 - import android.hardware.usb.UsbEndpoint;
 - import android.hardware.usb.UsbInterface;
 - import android.hardware.usb.UsbManager;
 - import android.util.Log;
 - import android.widget.Toast;
 - /**
 - * Created by DAI on 2016/1/23.
 - * Author:Will Smith
 - * Email:15997135562@163.com
 - *
 - * Tip:
 - *before developing USB on Android,you should configure manifests
 - * accoriding to Android Developer
 - */
 - public class USB_Admin {
 - private UsbManager usbManager;
 - private UsbDevice usbDevice;
 - private UsbInterface usbInterface;
 - private UsbEndpoint usbEndpointIn;
 - private UsbEndpoint usbEndpointOut;
 - private UsbDeviceConnection usbDeviceConnection;
 - private static int TIMEOUT = 5000;
 - /*自己编写的USB管理类的构造函数*/
 - public USB_Admin(Context context){
 - usbManager = (UsbManager) context.getSystemService(Context.USB_SERVICE);
 - Log.v("USBManager:","" + usbManager);
 - }
 - /*****************************USB相关的操作**********************************/
 - /*获得USB的usbManager*/
 - public UsbManager get_UsbManager(){
 - return usbManager;
 - }
 - /*获得USB设备*/
 - public UsbDevice get_UsbDevice(Intent intent){ //这个USBDevice还有问题,暂时还得不到;
 - /*使用意图过滤器的方法*/
 - if (intent != null) {
 - Log.d("intent: ", "" + intent.toString());
 - if (intent.getAction().equals(UsbManager.ACTION_USB_DEVICE_ATTACHED)) { //说明没有进入到这个if语句中
 - usbDevice = intent.getParcelableExtra(UsbManager.EXTRA_DEVICE); //待查找;
 - Log.v("USBDevice ","" + usbDevice);
 - if (usbDevice != null) {
 - Log.d("USB device attached: ", "" + usbDevice.getDeviceName());
 - }
 - }
 - }
 - /*使用枚举的方法做一下*/
 - return usbDevice;
 - }
 - /*获得访问USB设备的权限*/
 - /*若没有在清单文件中配置USB的意图过滤器,那么就需要手动通过这一步去获取权限*/
 - /*
 - public void getPermission(){
 - }
 - */
 - /*获取USB设备的UsbInterface*/
 - /*和系统提供的函数名有冲突*/
 - public UsbInterface get_Interface(Context context){
 - usbInterface = usbDevice.getInterface(0);
 - Log.v("USBInterface:", "" + usbInterface);
 - if(usbInterface == null){
 - Toast.makeText(context,"can't get usbInterface",Toast.LENGTH_SHORT);
 - return null;
 - }
 - return usbInterface;
 - }
 - /*
 - 作用:获取USB设备UsbEndpoint
 - 参数:
 - 0:表示获取输入端点
 - 1:表示获取输出端点
 - */
 - /*和系统提供的函数名有冲突*/
 - public UsbEndpoint get_Endpoint(int i,Context context){
 - //获取输入端点
 - if(i == 0){
 - if((usbEndpointIn = usbInterface.getEndpoint(0)) != null){
 - Log.v("USBEndpointIn:","" + usbEndpointIn);
 - return usbEndpointIn;
 - }
 - Toast.makeText(context,"can't get usbEndpointIn",Toast.LENGTH_SHORT);
 - }else if(i == 1){ //获取输出端点
 - if((usbEndpointOut = usbInterface.getEndpoint(1)) != null){
 - Log.v("USBEndpointOut:","" + usbEndpointOut);
 - return usbEndpointOut;
 - }
 - Toast.makeText(context,"can't get usbEndpointOut",Toast.LENGTH_SHORT);
 - }
 - Toast.makeText(context,"can't get any usbEndpoint",Toast.LENGTH_SHORT);
 - return null;
 - }
 - /*获得USB设备的UsbDeviceConnection*/
 - public UsbDeviceConnection get_usbDeviceConnection(Context context){
 - if(usbManager.hasPermission(usbDevice)){
 - usbDeviceConnection = usbManager.openDevice(usbDevice);
 - Log.v("USBDeviceConnection:","" + usbDeviceConnection);
 - return usbDeviceConnection;
 - }
 - Toast.makeText(context,"can't get usbDeviceConnection",Toast.LENGTH_SHORT);
 - return null;
 - }
 - /*接收数据*/
 - public int receive_Message(byte[] receiveBytes){
 - int ret = -1;
 - if(usbEndpointIn != null){
 - ret = usbDeviceConnection.bulkTransfer(usbEndpointIn, receiveBytes, receiveBytes.length, TIMEOUT);
 - }else {
 - Log.v("receiveBytes: ", "failed");
 - }
 - return ret;
 - }
 - /*发送数据*/
 - public int send_Message(byte[] sendBytes){
 - int ret = -1;
 - if(usbEndpointOut != null){
 - ret = usbDeviceConnection.bulkTransfer(usbEndpointOut, sendBytes, sendBytes.length, TIMEOUT);
 - }else {
 - Log.v("Send: ","failed");
 - }
 - return ret;
 - }
 - /*断开已连接的USB设备*/
 - public void disconnect_USB(Context context){
 - BroadcastReceiver mUsbReceiver = new BroadcastReceiver() {
 - public void onReceive(Context context, Intent intent) {
 - String action = intent.getAction();
 - if (UsbManager.ACTION_USB_DEVICE_DETACHED.equals(action)) {
 - UsbDevice device = (UsbDevice)intent.getParcelableExtra(UsbManager.EXTRA_DEVICE);
 - if (device != null) {
 - usbDeviceConnection.releaseInterface(get_Interface(context));
 - usbDeviceConnection.close();
 - }
 - }
 - }
 - };
 - }
 - /*获得设备的product-id和vendor-id*/
 - public int get_ProductId(){
 - return usbDevice.getProductId();
 - }
 - /*获得设备的vendor-id*/
 - public int get_VendorId(){
 - return usbDevice.getVendorId();
 - }
 - /*获得设备的getSerialNumber*/
 - /*
 - public String get_SerialNumber(){
 - return null;
 - }
 - */
 - }
 
UsbTestActivity:
- package com.example.dai.usb_test;
 - import android.content.Intent;
 - import android.hardware.usb.UsbDevice;
 - import android.hardware.usb.UsbDeviceConnection;
 - import android.hardware.usb.UsbEndpoint;
 - import android.hardware.usb.UsbInterface;
 - import android.hardware.usb.UsbManager;
 - import android.os.Bundle;
 - import android.os.Message;
 - import android.support.design.widget.FloatingActionButton;
 - import android.support.design.widget.Snackbar;
 - import android.support.v7.app.AppCompatActivity;
 - import android.support.v7.widget.Toolbar;
 - import android.util.Log;
 - import android.view.Menu;
 - import android.view.MenuItem;
 - import android.view.View;
 - import android.widget.EditText;
 - import java.io.UnsupportedEncodingException;
 - /*Purpose:
 - *
 - * test USB on Android by receiving data from stm32 board,
 - * then display on X4418 board
 - *
 - * */
 - public class UsbTestActivity extends AppCompatActivity {
 - private USB_Admin usb_admin;
 - private UsbManager usbManager;
 - private UsbDevice usbDevice;
 - private UsbInterface usbInterface;
 - private UsbDeviceConnection usbDeviceConnection;
 - private UsbEndpoint usbEndpointIn;
 - private UsbEndpoint usbEndpointOut;
 - protected final Object mReadBufferLock = new Object();
 - protected final Object mWriteBufferLock = new Object();
 - byte[] receiveBytes = new byte[32];
 - byte[] sendBytes = new byte[32];
 - private StringBuffer stringBuffer = new StringBuffer();
 - EditText editText;
 - @Override
 - protected void onCreate(Bundle savedInstanceState) {
 - super.onCreate(savedInstanceState);
 - setContentView(R.layout.activity_usb_test);
 - Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
 - setSupportActionBar(toolbar);
 - FloatingActionButton fab = (FloatingActionButton) findViewById(R.id.fab);
 - fab.setOnClickListener(new View.OnClickListener() {
 - @Override
 - public void onClick(View view) {
 - Snackbar.make(view, "Replace with your own action", Snackbar.LENGTH_LONG)
 - .setAction("Action", null).show();
 - }
 - });
 - editText = (EditText)findViewById(R.id.editText);
 - usb_Init();
 - usb_receiveData();
 - usb_sendData();
 - }
 - public void usb_Init(){
 - Intent intent = getIntent();
 - usb_admin = new USB_Admin(this);
 - Log.v("usb_admin: ", "" + usb_admin);
 - usbManager = usb_admin.get_UsbManager();
 - Log.v("usbManager: ","" + usbManager);
 - usbDevice = usb_admin.get_UsbDevice(intent);
 - Log.v("usbDevice: ", "" + usbDevice);
 - Log.v("interfaceCount: ",""+usbDevice.getInterfaceCount());
 - usbInterface = usb_admin.get_Interface(this);
 - Log.v("usbInterface: ", "" + usbInterface); //1个;
 - Log.v("usbEndpointCount: ", "" + usbInterface.getEndpointCount());
 - usbEndpointIn = usb_admin.get_Endpoint(0, this);
 - Log.v("usbEndpointIn: ", "" + usbEndpointIn);
 - Log.v("usbEndpointDirection: ", "" + usbEndpointIn.getDirection());
 - usbEndpointOut = usb_admin.get_Endpoint(1, this);
 - Log.v("usbEndpointOut: ", "" + usbEndpointOut);
 - Log.v("usbEndpointDirection: ", "" + usbEndpointOut.getDirection());
 - usbDeviceConnection = usb_admin.get_usbDeviceConnection(this);
 - Log.v("usbDeviceConnection: ", "" + usbDeviceConnection);
 - configUsb340(115200);
 - }
 - public void usb_receiveData(){
 - ReceiveThread receiveThread = new ReceiveThread();
 - Thread thread = new Thread(receiveThread);
 - thread.start();
 - }
 - public void usb_sendData(){
 - SendThread sendThread = new SendThread();
 - Thread send = new Thread(sendThread);
 - send.start();
 - }
 - class ReceiveThread implements Runnable{
 - @Override
 - public void run() {
 - synchronized(mReadBufferLock){
 - while (!Thread.currentThread().isInterrupted()){
 - if(usbDeviceConnection.claimInterface(usbInterface, true)){
 - if((usb_admin.receive_Message(receiveBytes)) >= 0){
 - /*
 - for(int i=0;i<receiveBytes.length;i++){
 - Log.v("Data: ",""+receiveBytes[i]); //为什么这里得到的数据大部分都为0呢?
 - }
 - */
 - Log.v("length: ",""+usb_admin.receive_Message(receiveBytes));
 - String string = null;
 - Log.v("receiveBytes: ","" + receiveBytes.toString());
 - Log.v("receiveBytes: ","is OK ");
 - try {
 - string = new String(receiveBytes,"UTF-8");
 - stringBuffer.append(string);
 - Log.v("3D DATA", string);
 - } catch (UnsupportedEncodingException e) {
 - e.printStackTrace();
 - }
 - Message message = handler.obtainMessage();
 - message.obj = stringBuffer;
 - message.what = 1;
 - handler.sendMessage(message);
 - }else {
 - Log.v("Receive Data: ","failed");
 - }
 - }else {
 - Log.v("claimInterface: ","failed");
 - }
 - try {
 - Thread.sleep(3000);
 - } catch (InterruptedException e) {
 - e.printStackTrace();
 - }
 - }
 - }
 - }
 - }
 - class SendThread implements Runnable{
 - @Override
 - public void run() {
 - synchronized(mWriteBufferLock){
 - while (!Thread.currentThread().isInterrupted()){
 - if(usbDeviceConnection.claimInterface(usbInterface, true)){
 - String string = " Android USB Test ";
 - sendBytes = string.getBytes();
 - if((usb_admin.send_Message(sendBytes)) >= 0){
 - Log.v("sendBytes: ","is OK ");
 - }else {
 - Log.v("Send Data: ","failed");
 - }
 - }else {
 - Log.v("claimInterface: ","failed");
 - }
 - try {
 - Thread.sleep(3000);
 - } catch (InterruptedException e) {
 - e.printStackTrace();
 - }
 - }
 - }
 - }
 - }
 - private android.os.Handler handler = new android.os.Handler(){
 - @Override
 - public void handleMessage(Message msg) {
 - super.handleMessage(msg);
 - switch (msg.what){
 - case 1:
 - editText.setText((StringBuffer)msg.obj);
 - break;
 - default:
 - break;
 - }
 - }
 - };
 - @Override
 - public boolean onCreateOptionsMenu(Menu menu) {
 - // Inflate the menu; this adds items to the action bar if it is present.
 - getMenuInflater().inflate(R.menu.menu_usb_test, menu);
 - return true;
 - }
 - @Override
 - public boolean onOptionsItemSelected(MenuItem item) {
 - // Handle action bar item clicks here. The action bar will
 - // automatically handle clicks on the Home/Up button, so long
 - // as you specify a parent activity in AndroidManifest.xml.
 - int id = item.getItemId();
 - //noinspection SimplifiableIfStatement
 - if (id == R.id.action_settings) {
 - return true;
 - }
 - return super.onOptionsItemSelected(item);
 - }
 - private boolean configUsb340(int paramInt)
 - {
 - byte[] arrayOfByte = new byte[8];
 - usbDeviceConnection.controlTransfer(192, 95, 0, 0, arrayOfByte, 8, 1000);
 - usbDeviceConnection.controlTransfer(64, 161, 0, 0, null, 0, 1000);
 - long l1 = 1532620800 / paramInt;
 - for (int i = 3; ; i--)
 - {
 - if ((l1 <= 65520L) || (i <= 0))
 - {
 - long l2 = 65536L - l1;
 - int j = (short)(int)(0xFF00 & l2 | i);
 - int k = (short)(int)(0xFF & l2);
 - usbDeviceConnection.controlTransfer(64, 154, 4882, j, null, 0, 1000);
 - usbDeviceConnection.controlTransfer(64, 154, 3884, k, null, 0, 1000);
 - usbDeviceConnection.controlTransfer(192, 149, 9496, 0, arrayOfByte, 8, 1000);
 - usbDeviceConnection.controlTransfer(64, 154, 1304, 80, null, 0, 1000);
 - usbDeviceConnection.controlTransfer(64, 161, 20511, 55562, null, 0, 1000);
 - usbDeviceConnection.controlTransfer(64, 154, 4882, j, null, 0, 1000);
 - usbDeviceConnection.controlTransfer(64, 154, 3884, k, null, 0, 1000);
 - usbDeviceConnection.controlTransfer(64, 164, 0, 0, null, 0, 1000);
 - return true;
 - }
 - l1 >>= 3;
 - }
 - }
 - }
 
从STM32发送数据那段的程序如下:
- #include "sys.h"
 - #include "delay.h"
 - #include "uart.h"
 - #include "led.h"
 - int main(void){
 - int i = 0;
 - char res[10] = {'0','1','2','3','4','5','6','7','8','9'}; //ASCII:49-57
 - Stm32_Clock_Init(336,8,2,7);//ʨ׃ʱד,168Mhz
 - delay_init(168);
 - USART_Init();
 - while(1){
 - for(i=0;i<10;i++){
 - USART1->DR = res[i];
 - while(((USART1->SR)&(0x80)) != 0x80);
 - }
 - delay_ms(3000);
 - }
 - }
 
效果图如下:
注:针对不同的USB转串口芯片,USB部分的配置代码不一样;本程序只针对CH340芯片可用;
具体的USB转串口程序可参考Github上的开源项目https://github.com/ksksue/PhysicaloidLibrary
或者 https://github.com/mik3y/usb-serial-for-android
                    
                
                
            
        
浙公网安备 33010602011771号