由于最近公司项目要连接一个usb转串口的设备,之前没有搞过这个,于是就各种网上找资料了
1.首先我们得了解安卓的usb编程,我是参考了这篇博客http://blog.csdn.net/tianruxishui/article/details/38338087,里面讲解的很清楚,其实安卓串口转usb就是usb接收的数据还要经过那个usb转串口芯片的处理,也就需要数据处理的代码,相当于是安卓的驱动。
我自己也写了demo上传到了github,大家可以看看 了解一下安卓usb编程https://github.com/tangchao5206/AndroidUsb。
有很多常见的usb转串口的芯片,比如ch340系列,pl2303,一般这些芯片网上都能找到安卓的驱动,我用的是ch340
这些百度上一搜就能找到
点击下载即可,里面有安卓demo实例。
2.当然开始用安卓调设备之前,我们先应该用电脑串口工具
接收一下设备的数据对不对,这里就可参照你设备的通讯协议文档了
这里所说的波特率,校验位,数据位,停止位,一般
设备的协议文档上会给出,学过硬件的一下应该就懂了。
接收的数据跟协议文档上的对的上,说明设备没问题,这时我们就可以开始用安卓调了(因为可能有些设备是坏的,一步一步确定无误最好)
3.官方demo里,可以看到有个CH34xUARTDriver.jar的jar包,这里面就是他对芯片接受到的数据进行的处理,方法大致都封装好了,我们直接引入,调用就可以了。下面开始贴上我的代码了,也是参照那个demo
写的
public class Ch34Service extends Service {
private static final String TAG ="SanHeYiCKService" ;
private SanheyiBinder mBinder = new SanheyiBinder();
private Ch34Callback callback;
private static final String ACTION_USB_PERMISSION = "cn.wch.wchusbdriver.USB_PERMISSION";
public byte[] writeBuffer;
public byte[] readBuffer;
private boolean isOpen;
public int baudRate;//波特率
public byte stopBit;//停止位
public byte dataBit;//数据位
public byte parity;
public byte flowControl;
String num1;
String number;
private readThread mreadThread;
public String ACTION_NO_INSERT="no insert";
public String ACTION_SUCCESS="success";
public String ACTION_ERROR="error";
private int device;//0三诺血糖仪 1 倍稳血糖仪
@Override
public IBinder onBind(Intent intent) {
mBinder.setService(Ch34Service.this);
return mBinder;
}
public void setMsgCallback(Ch34Callback back,int type) {
this.callback = back;
this.device=type;
if (callback!=null){
measure();//开始测量
}
}
@Override
public void onCreate() {
super.onCreate();
BaseApplication.driver = new CH34xUARTDriver(
(UsbManager) getSystemService(Context.USB_SERVICE), this,
ACTION_USB_PERMISSION);
baudRate = 9600;
/* stop bits */
/* default is stop bit 1 */
stopBit = 1;
/* data bits */
dataBit = 8;
/* default is none */
parity = 0;
flowControl = 0;
if (!BaseApplication.driver.UsbFeatureSupported())// 判断系统是否支持USB HOST
{
Dialog dialog = new AlertDialog.Builder(this)
.setTitle("提示")
.setPositiveButton("确认",
new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface arg0,
int arg1) {
System.exit(0);
}
}).create();
dialog.setCanceledOnTouchOutside(false);
dialog.show();
}
//getActivity().getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);// 保持常亮的屏幕的状态
writeBuffer = new byte[512];
readBuffer = new byte[512];
isOpen = false;
}
private void measure() {
if (!isOpen&& BaseApplication.driver != null) {
if (!BaseApplication.driver.ResumeUsbList())// ResumeUsbList方法用于枚举CH34X设备以及打开相关设备
{
callback.OnMessage("no insert");
BaseApplication.driver.CloseDevice();
} else {
if (!BaseApplication.driver.UartInit()) {//对串口设备进行初始化操作
return;
}
if (BaseApplication.driver != null) {
boolean b = BaseApplication.driver.SetConfig(baudRate, dataBit, stopBit, parity, flowControl);
if (b) {
callback.OnMessage("success");
isOpen = true;
mreadThread = new readThread();
mreadThread.start();
//开启读线程读取串口接收的数据
} else {
callback.OnMessage("error");
Log.d(TAG,"error");
}
}
}
} else {
BaseApplication.driver.CloseDevice();
isOpen = false;
}
}
//读取数据的线程
private class readThread extends Thread {
public void run() {
byte [] buffer = new byte[15];
int bytes;
//这里就是我对不同设备进行的数据处理,然后通过接口回调回传数据
while (isOpen) {
bytes = BaseApplication.driver.ReadData(buffer,15);
byte[] buf = new byte[bytes];
System.arraycopy(buffer, 0, buf, 0, bytes);
String recv = StringbyteUtils.toHexString(buf, bytes);
if (device==0) {
if (buf.length == 15 && buf[5] == 0x04 && buf[0] == 0x53 && buf[1] == 0x4e) {
callback.OnReceiveData(buf);//回传数据
} else if (buf.length == 9 && buf[5] == 0x02 && buf[0] == 0x53 && buf[1] == 0x4e) {
if (buf[6] == 0x01 && buf[7] == 0x01) {
callback.OnReceive("33.5");//回传数据
} else if (buf[6] == 0x01 && buf[7] == 0x02) {
callback.OnReceive("1.0");//回传数据
}
}
} else if (device==1){//device=1
if (buf.length == 9 ){
if (buf[0] == 0x55 && buf[2] == 0x06 && buf[3] == 0x05){
callback.OnReceiveData(buf);
}
}else if (buf.length==6){
// LogUtil.d(TAG,"bwdevice--"+buf[4]);
if (buf[0] == 0x55 && buf[2] == 0x03 && buf[3] == 0x04 && buf[4] == 0x04 ){
callback.OnReceive("1.0");//回传数据
}else if (buf[0] == 0x55 && buf[2] == 0x03 && buf[3] == 0x05 && buf[4] == 0x05){
callback.OnReceive("33.5");//回传数据
}
}
}
try {
Thread.sleep(2000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
@Override
public void onDestroy() {
super.onDestroy();
isOpen = false;
if (mreadThread != null){
mreadThread.interrupt();
mreadThread=null;
}
if (BaseApplication.driver!=null){
BaseApplication.driver.CloseDevice();
}
}
public class SanheyiBinder extends Binder {
private Ch34Service service;
public void setService(Ch34Service service) {
this.service = service;
}
public Ch34Service getService() {
return this.service;
}
}
流程也就是配置好前面所说的波特率那些参数,打开ch34
0芯片,然后就可以获得一个输入流,输出流的东西,通过这个我们就可以读写设备的数据,进行数据交换,一般协议文档上会给出的数据是十六进制的,我们参照他的要求解析就是,这里用位用算解析数据最快了
https://github.com/tangchao5206/Android_CH34UARTDemo
第一次,写博客,如有不足,还忘大家多多关照。