您好我正在开发一个名为PetScanner的项目。当我发送" g"我必须做可以与USB串口设备通信的项目。获取在USB设备上检查我必须得到一条消息,如" 0x2A"但我无法完成该计划,因为我不知道如何继续。 请帮助我谢谢!!
这是MainActivity;
package dls.readerapp;
import android.app.Activity;
import android.app.PendingIntent;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.pm.ActivityInfo;
import android.hardware.usb.UsbDevice;
import android.hardware.usb.UsbManager;
import android.hardware.usb.UsbDeviceConnection;
import android.hardware.usb.UsbEndpoint;
import android.hardware.usb.UsbInterface;
import android.media.AudioManager;
import android.os.BatteryManager;
import android.os.Bundle;
import android.os.CountDownTimer;
import android.os.Handler;
import android.os.Message;
import android.view.View;
import android.widget.Button;
import android.widget.ProgressBar;
import android.widget.TextView;
import com.android.volley.AuthFailureError;
import com.android.volley.DefaultRetryPolicy;
import com.android.volley.Request;
import com.android.volley.RequestQueue;
import com.android.volley.Response;
import com.android.volley.VolleyError;
import com.android.volley.VolleyLog;
import com.android.volley.toolbox.StringRequest;
import com.android.volley.toolbox.Volley;
import org.json.JSONException;
import org.json.JSONObject;
import java.lang.String;
import java.io.OutputStream;
import java.nio.charset.Charset;
import java.io.UnsupportedEncodingException;
import java.util.Iterator;
public class MainActivity extends Activity {
//Static property to know if activity is running or now - viz StartReceiver
public static Boolean Running = null;
float fullVoltage;
int batteryVol;
String currentBatteryVol = "Current Input Voltage:";
//Instance of class which works with reader - viz ReaderManager
private ReaderManager readerManager = null;
//Instance of ui elements
private Button mainButton = null;
private Button button10 = null;
private Button button = null;
private Button button2 = null;
private Button button3 = null;
private Button button4 = null;
private Button button5 = null;
private Button button6 = null;
private Button button7 = null;
private Button button8 = null;
private ProgressBar scanProgressBar = null;
private TextView infoTextView = null;
private TextView textView = null;
private IntentFilter intentfilter = null;
private String outputString = null;
private String serialNumber = null;
private Handler handler = null;
private UsbDeviceConnection usbDeviceConnection = null;
private UsbDevice usbDevice = null;
private UsbInterface usbInterface = null;
private UsbManager usbManager = null;
//Timer to make progressbar effect
private CountDownTimer timer = null;
//handler for sending event back to activity from readerManager
private Handler logHandler = null;
public void setCharacter(String outputString) {this.outputString = outputString; }
public String getSerialNumber(){
if(serialNumber == null){
usbDeviceConnection = usbManager.openDevice(usbDevice);
serialNumber = usbDeviceConnection.getSerial();
usbDeviceConnection.close();
}
return serialNumber;
}
private BroadcastReceiver broadcastreceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
//give the Input Voltage of the device
batteryVol = intent.getIntExtra(BatteryManager.EXTRA_VOLTAGE, 0);
}
};
private BroadcastReceiver broadcastreceiverr = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
//give the Input Voltage of the device
batteryVol = intent.getIntExtra(BatteryManager.EXTRA_VOLTAGE, 0);
}
};
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
//To prevent unneeded changing to landscape
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
setVolumeControlStream(AudioManager.STREAM_MUSIC);
//Indicator that activity is running
Running = true;
//Initialization of Volley - for communicating with server
final RequestQueue queue = Volley.newRequestQueue(this);
//Register usbReceiver to get Usb events + own intent ("own.usb.action") to call receiver whenever i want
BroadcastReceiver usbReceiver = new UsbReceiver();
final IntentFilter intentFilter = new IntentFilter(UsbManager.ACTION_USB_DEVICE_ATTACHED);
intentFilter.addAction(UsbManager.ACTION_USB_DEVICE_DETACHED);
intentFilter.addAction(UsbManager.EXTRA_PERMISSION_GRANTED);
intentFilter.addAction("own.usb.action");
this.registerReceiver(usbReceiver, intentFilter);
//Initialization of timer - CountDownTimer seemed to be most easy way
timer = new CountDownTimer(100000, 50) {
//decrementing progress bar to add effect that reader's going away
public void onTick(long millisUntilFinished) {
if (scanProgressBar.getProgress() > 0) {
scanProgressBar.incrementProgressBy(-2);
}
}
//if reader wasn't find in 100s close scanning
public void onFinish() {
readerManager.close();
infoTextView.append("Scanning Stopped\n");
mainButton.setText("Start A");
}
};
//get instances of ui elements
infoTextView = (TextView) findViewById(R.id.InfoTextView);
textView = (TextView) findViewById(R.id.textView);
mainButton = (Button) findViewById(R.id.mainButton);
button = (Button) findViewById(R.id.button);
button2 = (Button) findViewById(R.id.button2);
button3 = (Button) findViewById(R.id.button3);
button4 = (Button) findViewById(R.id.button4);
button5 = (Button) findViewById(R.id.button5);
button6 = (Button) findViewById(R.id.button6);
button7 = (Button) findViewById(R.id.button7);
button8 = (Button) findViewById(R.id.button8);
button10 = (Button) findViewById(R.id.button10);
scanProgressBar = (ProgressBar) findViewById(R.id.ScanProgressBar);
intentfilter = new IntentFilter(Intent.ACTION_BATTERY_CHANGED);
//add click listener
mainButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
//control if reader is plugged
if (readerManager != null) {
if (!readerManager.getScanning()) {
//if don't running start scanning
new Thread(readerManager).start();
timer.start();
infoTextView.setText("Scanning started\n");
mainButton.setText("Stop A");
//give the visibility of the button
button.setVisibility(View.VISIBLE);
button2.setVisibility(View.VISIBLE);
button3.setVisibility(View.VISIBLE);
button4.setVisibility(View.VISIBLE);
button5.setVisibility(View.VISIBLE);
button6.setVisibility(View.VISIBLE);
button7.setVisibility(View.VISIBLE);
button8.setVisibility(View.VISIBLE);
button10.setVisibility(View.VISIBLE);
textView.setVisibility(View.VISIBLE);
} else {
//else close communication
readerManager.close();
timer.cancel();
scanProgressBar.setProgress(0);
infoTextView.append("Scanning Stopped\n");
mainButton.setText("Start A");
//give the visibility of the button
button.setVisibility(View.VISIBLE);
button2.setVisibility(View.VISIBLE);
button3.setVisibility(View.VISIBLE);
button4.setVisibility(View.VISIBLE);
button5.setVisibility(View.VISIBLE);
button6.setVisibility(View.VISIBLE);
button7.setVisibility(View.VISIBLE);
button8.setVisibility(View.VISIBLE);
button10.setVisibility(View.VISIBLE);
textView.setVisibility(View.VISIBLE);
}
}
}
});
//different button operation
button2.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (readerManager != null) {
//readerManager.send("c0a\n");
textView.setText("Gain set to 0x0A\n");
infoTextView.setText("Gain c0a\n");
readerManager.setScanning(false);
mainButton.setText("Start A");
textView.setVisibility(View.INVISIBLE);
}
}
});
button3.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (readerManager != null) {
//readerManager.send("c2a\n");
//textView.setText("");
textView.setText("Gain set to 0x2A\n");
infoTextView.setText("Gain c2a\n");
readerManager.setScanning(false);
mainButton.setText("Start A");
textView.setVisibility(View.INVISIBLE);
}
}
});
button4.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (readerManager != null) {
//readerManager.send("c4a\n");
textView.setText("Gain set to 0x4A\n");
infoTextView.setText("Gain c4a\n");
readerManager.setScanning(false);
mainButton.setText("Start A");
textView.setVisibility(View.INVISIBLE);
}
}
});
button5.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (readerManager != null) {
//readerManager.send("c6a\n");
textView.setText("Gain set to 0x6A\n");
infoTextView.setText("Gain c6a\n");
readerManager.setScanning(false);
mainButton.setText("Start A");
textView.setVisibility(View.INVISIBLE);
}
}
});
button6.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (readerManager != null) {
String a = readerManager.send("g");
/*infoTextView.setText("0x2A");
/*textView.setVisibility(View.INVISIBLE);*/
//readerManager.send("Gain set to" + a + "\n");
textView.setVisibility(View.VISIBLE);
readerManager.setScanning(false);
mainButton.setText("Start A");
}
}
});
button7.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (readerManager != null) {
readerManager.setScanning(false);
mainButton.setText("Start A");
textView.setText("0x2A");
MainActivity.this.registerReceiver(broadcastreceiver, intentfilter);
fullVoltage = (float) (batteryVol * 0.001 + 1.185);
infoTextView.setText(currentBatteryVol + " " + fullVoltage + " volt");
textView.setVisibility(View.INVISIBLE);
}
}
});
button8.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (readerManager != null) {
readerManager.setScanning(false);
mainButton.setText("Start A");
textView.setText("0x2A");
MainActivity.this.registerReceiver(broadcastreceiverr, intentfilter);
fullVoltage = (float) (batteryVol * 0.001 + 1.1);
infoTextView.setText(currentBatteryVol + " " + fullVoltage + " volt");
textView.setVisibility(View.INVISIBLE);
}
}
});
button.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
infoTextView.setText("");
textView.setText("");
}
});
button10.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (readerManager != null) {
textView.setVisibility(View.INVISIBLE);
textView.setText("");
usbDeviceConnection = usbManager.openDevice(usbDevice);
serialNumber = usbDeviceConnection.getSerial();
infoTextView.setText("1699293DF3834F6F85C2\n79EEA5C6845200010001");
readerManager.setScanning(false);
mainButton.setText("Start A");
textView.setVisibility(View.INVISIBLE);
}
}
});
//crate instance of handler
logHandler = new Handler() {
@Override
public void handleMessage(Message message) {
if (message.what == 0) {
//if empty message only increment progressBar to add effect that reader's near
if (scanProgressBar.getProgress() < 100) {
scanProgressBar.incrementProgressBy(10);
}
}
if (message.what == 1) {
//if succsesful read then end progressBar effect
timer.cancel();
scanProgressBar.setProgress(0);
//inform user
infoTextView.append("Scan successful\n");
infoTextView.append("Waining for server...\n\n");
//start communication - sanding scanned encrypted id + initialization vector and serial number
String encID = (String) message.obj;
String serialNumber = readerManager.getSerialNumber();
JSONObject jsonBody = new JSONObject();
try {
//Encrypted VID, ID, Temperature(if a chip supports)\\\\\\\\\\\\
jsonBody.put("encryptedID", encID);
//User ID,
jsonBody.put("userID", "59aeb4edcb2d192cec094d8d");
// User Name
jsonBody.put("userName", "User Name");
} catch (JSONException e) {
e.printStackTrace();
}
final String requestBody = jsonBody.toString();
//using html POST - address of the server
//String url = "https://scans.petscanner.com/scans/create-scan"; //***needs ssl endpoint paid for on Heroku as they charge for this on custom domains
String url = "https://pet-scanner-api.herokuapp.com/scans/create-scan";
//Address of local the server
//String url = "http://192.168.1.5:3000/scans/create-scan";
StringRequest stringRequest = new StringRequest(Request.Method.POST, url,
new Response.Listener<String>() {
/*@Override
public void onResponse(String response) {
infoTextView.append(response);
}*/
@Override
public void onResponse(String response) {
//if successful print response (, -> ,\n to better visualization if json)j
JSONObject json = new JSONObject();
try {
json = new JSONObject(response);
infoTextView.append("ID: " + json.get("id") + "\n");
//infoTextView.append((String)json.get("status")+"\n");
infoTextView.append("Temperature " + json.get("temp") + "°C");
} catch (JSONException e) {
/*response = response.replaceAll(",", ",\n");
infoTextView.append(response);*/
}// create JSON obj from string
//infoTextView.append("Scanned message is:\n"+ response);
}
}, new Response.ErrorListener() {
@Override
public void onErrorResponse(VolleyError error) {
//if not inform user
infoTextView.append("Network error");
}
}) {
@Override
public String getBodyContentType() {
return "application/json; charset=utf-8";
}
@Override
public byte[] getBody() throws AuthFailureError {
try {
return requestBody == null ? null : requestBody.getBytes("utf-8");
} catch (UnsupportedEncodingException uee) {
VolleyLog.wtf("Unsupported Encoding while trying to get the bytes of %s using %s", requestBody, "utf-8");
return null;
}
}
};
stringRequest.setRetryPolicy(new DefaultRetryPolicy(12000,
DefaultRetryPolicy.DEFAULT_MAX_RETRIES, DefaultRetryPolicy.DEFAULT_BACKOFF_MULT));
queue.add(stringRequest);
mainButton.setText("Start A");
button.setVisibility(View.VISIBLE);
button2.setVisibility(View.VISIBLE);
button3.setVisibility(View.VISIBLE);
button4.setVisibility(View.VISIBLE);
button5.setVisibility(View.VISIBLE);
button6.setVisibility(View.VISIBLE);
button7.setVisibility(View.VISIBLE);
textView.setVisibility(View.INVISIBLE);
infoTextView.setVisibility(View.VISIBLE);
}
}
};
//call usb receiver on end of onCreate in case that device is already connected
Intent message = new Intent("own.usb.action");
intentFilter.addAction(UsbManager.ACTION_USB_DEVICE_DETACHED);
this.getApplicationContext().sendBroadcast(message);
}
//usb receiver catching all usb events in activity (inside activity cause it was most easy way to changing ui outside of activity
public class UsbReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
//get usb service and create empty device variable
UsbManager usbManager = (UsbManager) context.getSystemService(USB_SERVICE);
final IntentFilter intentFilter = new IntentFilter(UsbManager.ACTION_USB_DEVICE_ATTACHED);
intentFilter.addAction(UsbManager.ACTION_USB_DEVICE_DETACHED);
UsbDevice usbDevice = null;
//iterate over all usb devices to find one with desired vid (also pid) -
Iterator<UsbDevice> deviceIterator = usbManager.getDeviceList().values().iterator();
if (deviceIterator.hasNext()) {
UsbDevice device = deviceIterator.next();
if (device.getVendorId() == 0x04D8) {
//if find bring activity to front if already wasn't
Intent i = new Intent(context, MainActivity.class);
i.setFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
startActivity(i);
//save instance to variable
usbDevice = device;
}
}
if (usbDevice != null) {
if (usbManager.hasPermission(usbDevice)) {
//if has permission create instance of ReaderManager
readerManager = new ReaderManager(context, logHandler, usbDevice);
//start scanning
new Thread(readerManager).start();
timer.start();
infoTextView.setText("Scanning started\n");
mainButton.setText("Stop A");
} else {
//if hasn't permission request it
PendingIntent permissionIntent = PendingIntent.getBroadcast(context, 0, new Intent(UsbManager.EXTRA_PERMISSION_GRANTED), 0);
usbManager.requestPermission(usbDevice, permissionIntent);
}
} else if (readerManager != null) {
//if there isn't reader and readerManager was created - close scanning + inform user
readerManager.close();
mainButton.setText("NoReader");
}
}
}
}
答案 0 :(得分:-1)
以下是USB串口设备的ReaderManger代码:
package dls.readerapp;
import android.annotation.TargetApi;
import android.content.Context;
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.media.AudioManager;
import android.media.ToneGenerator;
import android.os.Build;
import android.os.Handler;
import android.os.Message;
import android.util.Log;
import java.io.OutputStream;
import java.nio.charset.Charset;
public class ReaderManager implements Runnable {
//1. bool to set closeRequested
private Boolean closeRequested = null;
//2. bool to get if scanning
private Boolean scanning = null;
//3. volumes of beep sound (min == usual sound, max == successful scan sound)
private Integer minVolume = null;
private Integer maxVoleme = null;
//4. string variable of character to send in communication
private String outputString = null;
private String serialNumber = null;
//5. instance of handler
private Handler handler = null;
//6.usb variables
private UsbDeviceConnection usbDeviceConnection = null;
private UsbDevice usbDevice = null;
private UsbInterface usbInterface = null;
private UsbManager usbManager = null;
//7. toneGenerator for beeping sound
private ToneGenerator toneGenerator = null;
public ReaderManager(Context context, Handler handler, UsbDevice usbDevice) {
//8. initialization to default values
this.closeRequested = false;
this.scanning = false;
this.minVolume = 80;
this.maxVoleme = 100;
this.outputString = "a";
//9. save handler and desired usbDevice
this.handler = handler;
this.usbDevice = usbDevice;
//10. get interface 1 where communication takes place
this.usbInterface = usbDevice.getInterface(1);
//11. get usbManger from context
this.usbManager = (UsbManager)context.getSystemService(Context.USB_SERVICE);
//initialization toneGenerator to min volume (only way i find to change volume is to create new instance)
this.toneGenerator = new ToneGenerator(AudioManager.STREAM_MUSIC, minVolume);
}
//12. change character to send
public void setCharacter(String outputString) {
this.outputString = outputString;
}
//13. get scanning status
public Boolean getScanning(){
return scanning;
}
public void setScanning(boolean b){
this.scanning = b;
}
//14. get serial number !!! permission needed !!!
public String getSerialNumber() {
if(serialNumber == null){
//15. if scanning wast start yet - it is needed to open new connection to get serial
usbDeviceConnection = usbManager.openDevice(usbDevice);
serialNumber = usbDeviceConnection.getSerial();
usbDeviceConnection.close();
}
return serialNumber;
}
//16. request close
public void close() {
closeRequested = true;
}
public String send(String out){
usbDeviceConnection = usbManager.openDevice(usbDevice);
usbDeviceConnection.claimInterface(usbInterface, true);
//17 .get serial number for latter use
serialNumber = usbDeviceConnection.getSerial();
//18. get endpoints (ways of communication) of interface
UsbEndpoint endpointIn = usbInterface.getEndpoint(1);
UsbEndpoint endpointOut = usbInterface.getEndpoint(0);
//19. crate variables for communication
byte[] readData = new byte[8];
byte[] sendData = out.getBytes(Charset.forName("US-ASCII"));
//20. send start character for communication
usbDeviceConnection.bulkTransfer(endpointOut, sendData, sendData.length, 100);
usbDeviceConnection.bulkTransfer(endpointIn, readData, readData.length, 100);
String result = new String(readData);
//if (result.length() < 1) {
return new String(readData);
/*} else {
return "?";
}*/
}
//21. main scanning method - !!! permission needed !!!
@Override
public void run() {
//22. set variables to desired values
scanning = true;
this.toneGenerator = new ToneGenerator(AudioManager.STREAM_MUSIC, minVolume);
//23. open communication and claim interface
usbDeviceConnection = usbManager.openDevice(usbDevice);
usbDeviceConnection.claimInterface(usbInterface, true);
//24. get serial number for latter use
serialNumber = usbDeviceConnection.getSerial();
//25. get endpoints (ways of communication) of interface
UsbEndpoint endpointIn = usbInterface.getEndpoint(1);
UsbEndpoint endpointOut = usbInterface.getEndpoint(0);
//26. crate variables for communication
byte[] readData = new byte[64];
byte[] sendData = outputString.getBytes(Charset.forName("US-ASCII"));
String finalMessage = "";
//27. send start character for communication
usbDeviceConnection.bulkTransfer(endpointOut, sendData, sendData.length, 500);
//28. main communication cycle
while (true) {
if (closeRequested) {
//29. if close requested close
closeRequested = false;
scanning = false;
this.send("g");
break;
}
//30. get message from scanner[]
usbDeviceConnection.bulkTransfer(endpointIn, readData, readData.length, 25);
//31. get actual string message
String message = new String(readData, Charset.forName("US-ASCII"));
message = message.substring(0, message.indexOf('\0'));
if (message.contains("*")) {
//32. if contains * then make short beep sound (means not chip is near)
handler.sendMessage(handler.obtainMessage(0));
toneGenerator.startTone(ToneGenerator.TONE_CDMA_ALERT_CALL_GUARD, 20);
}
if (message.length() == 32) {
//33. if message is 32 chars long means its either encrypted id or initialization vector
if (message.length() < 6) {
if (finalMessage != "") {
//34. if finalMessage isn't "" then it means first part was scanned -> successful read
//35. create new instance of toneGenerator to raise volume and play longer sound;
toneGenerator = new ToneGenerator(AudioManager.STREAM_MUSIC, maxVoleme);
toneGenerator.startTone(ToneGenerator.TONE_CDMA_ALERT_CALL_GUARD, 200);
//36. inform main thread
handler.sendMessage(handler.obtainMessage(1, finalMessage + message));
//37. sleep to let beep sound end
try {
Thread.sleep(250);
} catch (InterruptedException e) {
e.printStackTrace();
}
//38. close scanning
toneGenerator.release();
scanning = false;
break;
}
//39. if first 32 chars then save it to finalMessage
finalMessage = message;
}
//40. refresh buffer
readData = new byte[64];
}
}
}
}