def selectservice(): import _IOBluetoothUI gui = _IOBluetoothUI.IOBluetoothServiceBrowserController.serviceBrowserController_( _macutil.kIOBluetoothServiceBrowserControllerOptionsNone) # try to bring GUI to foreground by setting it as floating panel # (if this is called from pyobjc app, it would automatically be in foreground) try: gui.window().setFloatingPanel_(True) except: pass # show the window and wait for user's selection response = gui.runModal() if response == AppKit.NSRunStoppedResponse: results = gui.getResults() if len(results) > 0: # should always be > 0, but check anyway serviceinfo = _getservicetuple(results[0]) # sometimes the baseband connection stays open which causes # problems with connections ... so close it here, see if this fixes # it dev = _IOBluetooth.IOBluetoothDevice.withAddress_( _macutil.createbtdevaddr(serviceinfo[0])) if dev.isConnected(): dev.closeConnection() return serviceinfo # user cancelled selection return None
def connect(self, headers={}): if self.__client is None: if not BBLocalDevice.isPoweredOn(): raise OBEXError(_kOBEXSessionNoTransportError, "Bluetooth device not available") self.__delegate = _BBOBEXClientDelegate.alloc().initWithCallback_( self._finishedrequest) self.__client = BBBluetoothOBEXClient.alloc( ).initWithRemoteDeviceAddress_channelID_delegate_( _macutil.createbtdevaddr(self.__serveraddr[0]), self.__serveraddr[1], self.__delegate) if self.__obexsession is not None: self.__client.performSelector_withObject_( "setOBEXSession:", self.__obexsession) self.__reset() headerset = _headersdicttoset(headers) r = self.__client.sendConnectRequestWithHeaders_(headerset) if r != _kOBEXSuccess: self.__closetransport() raise OBEXError(r, "error starting Connect request (%s)" % errdesc(r)) _macutil.waituntil(self._done) if self.__error != _kOBEXSuccess: self.__closetransport() raise OBEXError( self.__error, "error during Connect request (%s)" % errdesc(self.__error)) resp = self.__getresponse() if resp.code != _obexcommon.OK: self.__closetransport() return resp
def connect(self, headers={}): if self.__client is None: if not BBLocalDevice.isPoweredOn(): raise OBEXError(_kOBEXSessionNoTransportError, "Bluetooth device not available") self.__delegate = _BBOBEXClientDelegate.alloc().initWithCallback_( self._finishedrequest) self.__client = BBBluetoothOBEXClient.alloc().initWithRemoteDeviceAddress_channelID_delegate_( _macutil.createbtdevaddr(self.__serveraddr[0]), self.__serveraddr[1], self.__delegate) if self.__obexsession is not None: self.__client.performSelector_withObject_("setOBEXSession:", self.__obexsession) self.__reset() headerset = _headersdicttoset(headers) r = self.__client.sendConnectRequestWithHeaders_(headerset) if r != _kOBEXSuccess: self.__closetransport() raise OBEXError(r, "error starting Connect request (%s)" % errdesc(r)) _macutil.waituntil(self._done) if self.__error != _kOBEXSuccess: self.__closetransport() raise OBEXError(self.__error, "error during Connect request (%s)" % errdesc(self.__error)) resp = self.__getresponse() if resp.code != _obexcommon.OK: self.__closetransport() return resp
def selectdevice(): import _IOBluetoothUI gui = _IOBluetoothUI.IOBluetoothDeviceSelectorController.deviceSelector() # try to bring GUI to foreground by setting it as floating panel # (if this is called from pyobjc app, it would automatically be in foreground) try: gui.window().setFloatingPanel_(True) except: pass # show the window and wait for user's selection response = gui.runModal() # problems here if transferring a lot of data?? if response == AppKit.NSRunStoppedResponse: results = gui.getResults() if len(results) > 0: # should always be > 0, but check anyway devinfo = _getdevicetuple(results[0]) # sometimes the baseband connection stays open which causes # problems with connections w so close it here, see if this fixes # it dev = _IOBluetooth.IOBluetoothDevice.withAddress_( _macutil.createbtdevaddr(devinfo[0])) if dev.isConnected(): dev.closeConnection() return devinfo # user cancelled selection return None
def findservices(addr=None, name=None, servicetype=None): if servicetype not in (_lightbluecommon.RFCOMM, _lightbluecommon.OBEX, None): raise ValueError("servicetype must be RFCOMM, OBEX or None, was %s" % \ servicetype) if addr is None: try: founddevices = finddevices() except _lightbluecommon.BluetoothError as e: msg = "findservices() failed, " +\ "error while finding devices: " + str(e) raise _lightbluecommon.BluetoothError(msg) #print founddevices addresses = [dev[0] for dev in founddevices] else: addresses = [addr] services = [] for devaddr in addresses: iobtdevice = _IOBluetooth.IOBluetoothDevice.withAddress_( _macutil.createbtdevaddr(devaddr)) try: lastseen = iobtdevice.getLastServicesUpdate() if lastseen is None or lastseen.timeIntervalSinceNow() < -2: # perform SDP query to update known services. # wait at least a few seconds between service discovery cos # sometimes it doesn't work if doing updates too often. # In future should have option to not do updates. serviceupdater = _SDPQueryRunner.alloc().init() try: serviceupdater.query(iobtdevice) # blocks until updated except _lightbluecommon.BluetoothError as e: msg = "findservices() couldn't get services for %s: %s" % \ (iobtdevice.getNameOrAddress(), str(e)) warnings.warn(msg) # or should I use cached services instead of warning? # but sometimes the cached ones are totally wrong. # if searching for RFCOMM, exclude OBEX services if servicetype == _lightbluecommon.RFCOMM: uuidbad = _macutil.PROTO_UUIDS.get(_lightbluecommon.OBEX) else: uuidbad = None filtered = _searchservices(iobtdevice, name=name, uuid=_macutil.PROTO_UUIDS.get(servicetype), uuidbad=uuidbad) #print "unfiltered:", iobtdevice.getServices() services.extend([_getservicetuple(s) for s in filtered]) finally: # close baseband connection (not sure if this is necessary, but # sometimes the transport connection seems to stay open?) iobtdevice.closeConnection() return services
def connect(self, address): if self.__isbound(): raise _socket.error("Can't connect, socket has been bound") elif self.__isconnected(): raise _socket.error("Socket is already connected") _checkaddrpair(address) # open a connection to device self.__remotedevice = _IOBluetooth.IOBluetoothDevice.withAddress_( _macutil.createbtdevaddr(address[0])) if not self.__remotedevice.isConnected(): if self.__timeout is None: result = self.__remotedevice.openConnection() else: result = self.__remotedevice.openConnection_withPageTimeout_authenticationRequired_( None, self.__timeout * 1000, False) if result != _macutil.kIOReturnSuccess: if result == _macutil.kBluetoothHCIErrorPageTimeout: if self.__timeout == 0: raise _socket.error( errno.EAGAIN, "Resource temporarily unavailable") else: raise _socket.timeout("connect timed out") else: raise _socket.error(result, "Cannot connect to %s, can't open connection." \ % str(address[0])) # open RFCOMM or L2CAP channel self.__eventlistener = self.__createlistener() result = self.__conn.connect( self.__remotedevice, address[1], self.__eventlistener) # pass listener as cocoa delegate if result != _macutil.kIOReturnSuccess: self.__remotedevice.closeConnection() self.__stopevents() self.__eventlistener = None raise _socket.error( result, "Cannot connect to %d on %s" % (address[1], address[0])) return # if you don't run the event loop a little here, it's likely you won't # be able to reconnect to the same remote device later _macutil.waitfor(0.5)
def finddevicename(address, usecache=True): if not _lightbluecommon._isbtaddr(address): raise TypeError("%s is not a valid bluetooth address" % str(address)) if address == gethostaddr(): return _gethostname() device = _IOBluetooth.IOBluetoothDevice.withAddress_(_macutil.createbtdevaddr(address)) if usecache: name = device.getName() if name is not None: return name # do name request with timeout of 10 seconds result = device.remoteNameRequest_withPageTimeout_(None, 10000) if result == _macutil.kIOReturnSuccess: return device.getName() raise _lightbluecommon.BluetoothError("Could not find device name for %s" % address)
def finddevicename(address, usecache=True): if not _lightbluecommon._isbtaddr(address): raise TypeError("%s is not a valid bluetooth address" % str(address)) if address == gethostaddr(): return _gethostname() device = _IOBluetooth.IOBluetoothDevice.withAddress_( _macutil.createbtdevaddr(address)) if usecache: name = device.getName() if name is not None: return name # do name request with timeout of 10 seconds result = device.remoteNameRequest_withPageTimeout_(None, 10000) if result == _macutil.kIOReturnSuccess: return device.getName() raise _lightbluecommon.BluetoothError("Could not find device name for %s" % address)
try: founddevices = finddevices() except _lightbluecommon.BluetoothError, e: msg = "findservices() failed, " +\ "error while finding devices: " + str(e) raise _lightbluecommon.BluetoothError(msg) #print founddevices addresses = [dev[0] for dev in founddevices] else: addresses = [addr] services = [] for devaddr in addresses: iobtdevice = _IOBluetooth.IOBluetoothDevice.withAddress_( _macutil.createbtdevaddr(devaddr)) try: lastseen = iobtdevice.getLastServicesUpdate() if lastseen is None or lastseen.timeIntervalSinceNow() < -2: # perform SDP query to update known services. # wait at least a few seconds between service discovery cos # sometimes it doesn't work if doing updates too often. # In future should have option to not do updates. serviceupdater = _SDPQueryRunner.alloc().init() try: serviceupdater.query(iobtdevice) # blocks until updated except _lightbluecommon.BluetoothError, e: msg = "findservices() couldn't get services for %s: %s" % \ (iobtdevice.getNameOrAddress(), str(e)) warnings.warn(msg)
if addr is None: try: founddevices = finddevices() except _lightbluecommon.BluetoothError, e: msg = "findservices() failed, " + "error while finding devices: " + str(e) raise _lightbluecommon.BluetoothError(msg) # print founddevices addresses = [dev[0] for dev in founddevices] else: addresses = [addr] services = [] for devaddr in addresses: iobtdevice = _IOBluetooth.IOBluetoothDevice.withAddress_(_macutil.createbtdevaddr(devaddr)) try: lastseen = iobtdevice.getLastServicesUpdate() if lastseen is None or lastseen.timeIntervalSinceNow() < -2: # perform SDP query to update known services. # wait at least a few seconds between service discovery cos # sometimes it doesn't work if doing updates too often. # In future should have option to not do updates. serviceupdater = _SDPQueryRunner.alloc().init() try: serviceupdater.query(iobtdevice) # blocks until updated except _lightbluecommon.BluetoothError, e: msg = "findservices() couldn't get services for %s: %s" % (iobtdevice.getNameOrAddress(), str(e)) warnings.warn(msg) # or should I use cached services instead of warning?
# Copyright (c) 2009 Bea Lam. All rights reserved.