Go to the documentation of this file.00001 package org.ros.rosserial;
00002
00003 import java.io.FileDescriptor;
00004 import java.io.FileInputStream;
00005 import java.io.FileOutputStream;
00006 import java.io.IOException;
00007
00008 import org.ros.message.rosserial_msgs.TopicInfo;
00009 import org.ros.rosserial.*;
00010
00011 import com.android.future.usb.UsbAccessory;
00012 import com.android.future.usb.UsbManager;
00013
00014
00015 import android.app.PendingIntent;
00016 import android.content.BroadcastReceiver;
00017 import android.content.Context;
00018 import android.content.Intent;
00019 import android.content.IntentFilter;
00020 import android.os.ParcelFileDescriptor;
00021 import android.util.Log;
00022
00023 import org.ros.node.Node;
00024
00025 public class ROSSerialADK {
00026
00027 static final String TAG= "ROSSerialADK";
00028 private static final String ACTION_USB_PERMISSION = "org.ros.rosserial.action.USB_PERMISSION";
00029
00030
00031 private ROSSerial rosserial;
00032 Thread ioThread;
00033
00034
00035 private Context mContext;
00036 private PendingIntent mPermissionIntent;
00037 boolean mPermissionRequestPending =false;
00038
00039 private UsbManager mUsbManager;
00040 UsbAccessory mAccessory;
00041 ParcelFileDescriptor mFileDescriptor;
00042 FileInputStream mInputStream;
00043 FileOutputStream mOutputStream;
00044 FileDescriptor fd;
00045
00046 private Node node;
00047
00048
00049 public interface onConnectionListener{
00050 public void trigger(boolean connection);
00051 }
00052
00053 private onConnectionListener connectionCB;
00054 public void setOnConnectonListener(onConnectionListener onConnectionListener){
00055 this.connectionCB = onConnectionListener;
00056 }
00057
00058
00059
00060 public ROSSerialADK( Context context, Node node){
00061
00062 this.node = node;
00063 this.mContext = context;
00064
00065 mUsbManager = UsbManager.getInstance(context);
00066 mPermissionIntent = PendingIntent.getBroadcast(context, 0, new Intent(
00067 ACTION_USB_PERMISSION), 0);
00068 IntentFilter filter = new IntentFilter(ACTION_USB_PERMISSION);
00069 filter.addAction(UsbManager.ACTION_USB_ACCESSORY_DETACHED);
00070 filter.addAction(UsbManager.ACTION_USB_ACCESSORY_ATTACHED);
00071 context.registerReceiver(mUsbReceiver, filter);
00072
00073 }
00074
00075
00076 private final BroadcastReceiver mUsbReceiver = new BroadcastReceiver() {
00077 @Override
00078 public void onReceive(Context context, Intent intent) {
00079 String action = intent.getAction();
00080 if (ACTION_USB_PERMISSION.equals(action)) {
00081 synchronized (this) {
00082 UsbAccessory accessory = UsbManager.getAccessory(intent);
00083 if (intent.getBooleanExtra(
00084 UsbManager.EXTRA_PERMISSION_GRANTED, false)) {
00085 openAccessory(accessory);
00086 } else {
00087 Log.d(TAG, "permission denied for accessory "
00088 + accessory);
00089 }
00090 mPermissionRequestPending = false;
00091 }
00092 } else if (UsbManager.ACTION_USB_ACCESSORY_DETACHED.equals(action)) {
00093 UsbAccessory accessory = UsbManager.getAccessory(intent);
00094 if (accessory != null && accessory.equals(mAccessory)) {
00095 closeAccessory();
00096 }
00097 }
00098 }
00099 };
00100
00101
00102
00103
00104 private static UsbAccessory getAccessory( UsbManager man){
00105 UsbAccessory[] accessories = man.getAccessoryList();
00106 if(accessories == null) return null;
00107
00108 for (UsbAccessory accessory : accessories){
00109 if (accessory !=null){
00110 if (accessory.getModel().equals("ROSSerialADK")
00111 && accessory.getManufacturer().equals("Willow Garage")){
00112 return accessory;
00113 }
00114 }
00115 }
00116
00117 return null;
00118
00119 }
00120
00121
00122 public static boolean isAttached(UsbManager man){
00123 if ( getAccessory(man) == null) return false;
00124 else return true;
00125 }
00126
00127 private boolean openAccessory(UsbAccessory accessory) {
00128 Log.d(TAG, "Opening Accessory!");
00129 mFileDescriptor = mUsbManager.openAccessory(accessory);
00130
00131 if (mFileDescriptor != null) {
00132
00133 mAccessory = accessory;
00134 fd = mFileDescriptor.getFileDescriptor();
00135 mInputStream = new FileInputStream(fd);
00136 mOutputStream = new FileOutputStream(fd);
00137
00138 rosserial = new ROSSerial(node, mInputStream, mOutputStream);
00139 ioThread = new Thread(null, rosserial, "ROSSerialADK");
00140 ioThread.setContextClassLoader(ROSSerialADK.class.getClassLoader());
00141 ioThread.start();
00142
00143 if (connectionCB != null) connectionCB.trigger(true);
00144 Log.v(TAG,"accessory opened");
00145 return true;
00146
00147 } else {
00148 Log.v(TAG,"accessory open fail");
00149 return false;
00150 }
00151 }
00152
00153
00154 public boolean open() {
00155
00156 UsbAccessory accessory = getAccessory(mUsbManager);
00157 if (accessory == null) {
00158 Log.v(TAG,"There is no ADK");
00159 return false;
00160 }
00161
00162 if (mUsbManager.hasPermission(accessory)) {
00163 return openAccessory(accessory);
00164 } else {
00165 synchronized (mUsbReceiver) {
00166 if (!mPermissionRequestPending) {
00167 mUsbManager.requestPermission(accessory,
00168 mPermissionIntent);
00169 mPermissionRequestPending = true;
00170 }
00171 }
00172 }
00173
00174 return true;
00175 }
00176
00177 private void closeAccessory() {
00178
00179 try {
00180 if (mFileDescriptor != null) {
00181 if(rosserial!=null) {
00182 rosserial.shutdown();
00183 rosserial = null;
00184 }
00185 mFileDescriptor.close();
00186 }
00187 } catch (IOException e) {
00188 } finally {
00189 mFileDescriptor = null;
00190 mAccessory = null;
00191 if (connectionCB != null) connectionCB.trigger(false);
00192
00193 }
00194 }
00195
00196 public void shutdown(){
00197 closeAccessory();
00198 mContext.unregisterReceiver(mUsbReceiver);
00199 }
00200
00201 public boolean isConnected(){
00202 return (mOutputStream != null);
00203 }
00204
00205
00206 TopicInfo[] getSubscriptions(){
00207 return rosserial.getSubscriptions();
00208 }
00209 TopicInfo[] getPublications(){
00210 return rosserial.getPublications();
00211 }
00212
00213
00214 void setOnSubscriptionCB(TopicRegistrationListener listener){
00215 if (rosserial!= null) rosserial.setOnNewSubcription(listener);
00216 }
00217
00218
00219 void setOnPublicationCB(TopicRegistrationListener listener){
00220 if (rosserial!= null) rosserial.setOnNewPublication(listener);
00221 }
00222
00223 }