00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031 import usb
00032 import time
00033 from math import pi
00034
00035 import roslib
00036 roslib.load_manifest('microscribe')
00037 import rospy
00038 from sensor_msgs.msg import *
00039 from joy.msg import *
00040
00041 import atexit
00042 atexit.register(rospy.signal_shutdown, 'exit')
00043
00044 rospy.init_node('microscribe', disable_signals=True)
00045
00046 def dump_list():
00047 for bus in usb.busses():
00048 print "%s" % bus
00049 for dev in bus.devices:
00050 print " ", dev.iManufacturer, dev.iProduct, dev.idProduct, dev.idVendor
00051
00052 def get_microscribes():
00053 ms = []
00054 for bus in usb.busses():
00055 for dev in bus.devices:
00056 if dev.idVendor == 0x0563 and dev.idProduct == 0x0050:
00057 ms.append(dev)
00058 return ms
00059
00060 def get_microscribe(serial_number = None):
00061 ms = get_microscribes()
00062 if serial_number is None:
00063 return ms[0]
00064 for dev in ms:
00065 h = dev.open()
00066 try:
00067 if h.getString(4, 100) == serial_number:
00068 return dev
00069 if dev.iSerialNumber == serial_number:
00070 return dev
00071 except usb.USBError:
00072 print "Difficulty opening %s" % dev
00073
00074
00075
00076 serial_number = None
00077 try:
00078 serial_number = rospy.get_param(rospy.get_name() + '/serial_number')
00079 except:
00080 pass
00081 ms = get_microscribe(serial_number)
00082
00083
00084 h = ms.open()
00085 try:
00086 h.detachKernelDriver(0)
00087 except:
00088 print "Didn't detach kernel driver"
00089 h.claimInterface(0)
00090 print "Opened microscribe:"
00091 for i in range(1,6):
00092 print " %s" % h.getString(i, 40)
00093
00094 def p_datum(datum):
00095 for i, d in enumerate(datum):
00096 if i in [2, 14, 16, 18]:
00097 print " ",
00098
00099 elif i in [4, 6, 8, 10, 12]:
00100 print "",
00101 print "%02x" % d,
00102
00103
00104 buttons = datum[1]
00105 buttons_str = ""
00106 if buttons & 1:
00107 buttons_str += 'G'
00108 else:
00109 buttons_str += ' '
00110 if buttons & 2:
00111 buttons_str += 'W'
00112 else:
00113 buttons_str += ' '
00114 print " [%s]" % buttons_str,
00115
00116
00117 time = datum[16] + datum[17] * 0x100
00118 print " %5i" % time,
00119
00120
00121 joint_d = datum[2:14]
00122 enc = []
00123 for i in range(6):
00124 enc.append(joint_d[2*i] + joint_d[2*i+1] * 0x100)
00125 print " ", enc,
00126
00127 print
00128
00129
00130 def lis():
00131 while True:
00132 try:
00133 datum = h.bulkRead(0x81, 100)
00134 p_datum(datum)
00135 except usb.USBError:
00136 time.sleep(0.1)
00137
00138 TICKS = [16000, 16000, 8000, 4000, 4000, 2000]
00139 REF = [2.756, pi, 8.0, 0, 6.4, 0]
00140
00141
00142 pub_joints = rospy.Publisher(rospy.get_name() + '/joint_states', JointState)
00143 pub_buttons = rospy.Publisher(rospy.get_name() + '/buttons', Joy)
00144
00145 def pub_loop():
00146 while True:
00147 try:
00148 datum = h.bulkRead(0x81, 100)
00149
00150 enc = []
00151 for i in range(6):
00152 enc.append(datum[2+2*i] + datum[2+2*i+1] * 0x100)
00153 if enc[0] > 50000:
00154 enc[0] = enc[0] - 0x10000
00155
00156 q = [2*pi * float(e) / float(T) - R for e, T, R in zip(enc, TICKS, REF)]
00157
00158
00159
00160
00161 msg = JointState()
00162 msg.header.stamp = rospy.get_rostime()
00163 msg.name = ['base_joint', 'shoulder_joint', 'elbow_joint',
00164 'wrist_roll_joint', 'wrist_flex_joint', 'stylus_joint']
00165 msg.position = q
00166 msg.velocity = [0] * 6
00167 msg.effort = [0] * 6
00168 pub_joints.publish(msg)
00169
00170 but = Joy()
00171 but.buttons = [0, 0]
00172 if datum[1] & 1:
00173 but.buttons[0] = 1
00174 if datum[1] & 2:
00175 but.buttons[1] = 1
00176 pub_buttons.publish(but)
00177 except usb.USBError:
00178 time.sleep(0.1)
00179
00180 pub_loop()
00181 '''
00182 handle.bulkRead(0x81, 30, 100)
00183
00184
00185
00186
00187 Bus 001 Device 012: ID 0563:0050 Immersion Corp.
00188 Device Descriptor:
00189 bLength 18
00190 bDescriptorType 1
00191 bcdUSB 2.00
00192 bDeviceClass 0 (Defined at Interface level)
00193 bDeviceSubClass 0
00194 bDeviceProtocol 0
00195 bMaxPacketSize0 8
00196 idVendor 0x0563 Immersion Corp.
00197 idProduct 0x0050
00198 bcdDevice 3.17
00199 iManufacturer 1
00200 iProduct 2
00201 iSerial 4
00202 bNumConfigurations 1
00203 Configuration Descriptor:
00204 bLength 9
00205 bDescriptorType 2
00206 wTotalLength 34
00207 bNumInterfaces 1
00208 bConfigurationValue 1
00209 iConfiguration 0
00210 bmAttributes 0x80
00211 (Bus Powered)
00212 MaxPower 500mA
00213 Interface Descriptor:
00214 bLength 9
00215 bDescriptorType 4
00216 bInterfaceNumber 0
00217 bAlternateSetting 0
00218 bNumEndpoints 1
00219 bInterfaceClass 3 Human Interface Device
00220 bInterfaceSubClass 0 No Subclass
00221 bInterfaceProtocol 0 None
00222 iInterface 0
00223 ** UNRECOGNIZED: 09 21 00 01 00 01 22 a6 01
00224 Endpoint Descriptor:
00225 bLength 7
00226 bDescriptorType 5
00227 bEndpointAddress 0x81 EP 1 IN
00228 bmAttributes 3
00229 Transfer Type Interrupt
00230 Synch Type None
00231 Usage Type Data
00232 wMaxPacketSize 0x0020 1x 32 bytes
00233 bInterval 1
00234
00235
00236 00 02 Constant
00237 01 00 Buttons
00238
00239 02 55 Changes with pan
00240 03 d7 ^^
00241
00242 04 3d Tilt?
00243 05 18
00244 06 09 Elbow?
00245 07 1a
00246 08 00 Cant?
00247 09 10
00248 10 e2 Flex?
00249 11 0c
00250 12 83 Roll?
00251 13 07
00252
00253 14 00 Constant
00254 15 00 ^^
00255
00256 16 31 Time in ms
00257 17 10 ^^
00258
00259 18 00 Constant
00260
00261
00262 Pan over 90 degrees:
00263 57969, 62023,
00264
00265 Tilt over 90 degrees:
00266 78, 4058,
00267
00268 Elbow over 90 degrees:
00269 10198, 8250,
00270
00271 Twist over 360 degrees:
00272 2164, 6145,
00273
00274 Flex over 90 degrees:
00275 2546, 3599,
00276
00277 Roll over 180 degrees:
00278 131, 1120
00279
00280 Ticks per revolution
00281 Pan 16216 (16000)
00282 Tilt 15920 (16000)
00283 Elbow 7792 ( 8000)
00284 Twist 3981 ( 4000)
00285 Flex 4212 ( 4000)
00286 Roll 1978 ( 2000)
00287
00288
00289 '''