Welcome!

Welcome to the official BlackBerry Support Community Forums.

This is your resource to discuss support topics with your peers, and learn from each other.

inside custom component

Java Development

Reply
Developer
timnelson
Posts: 102
Registered: ‎07-15-2008
My Device: Not Specified

Simple Bluetooth GPS code, could someone test?

I have paired down the GPS Demo code in order to illustrate a problem I am having with a Pearl 8100 (AT+T OS 4.2.1.X ) and a GlobalSat BT368i bluetooth GPS unit.  Once the application unit is out of range or off, there is no way to resume getting GPS fixes (even though I am following the error recovery logic documented by RIM).  I'd like to see if someone can give me a quick test using any GPS capable BB, so I can narrow down the error.  My current thought is that people have reported issues with bluetooth and OS 4.2.X, but I don't want to open a support incident unless I know it isn't just something silly I am doing.  Thanks for your help and input.

 

 

import net.rim.device.api.ui.*; import net.rim.device.api.ui.component.*; import net.rim.device.api.ui.container.*; import net.rim.device.api.system.*; import javax.microedition.location.*; public class GPSDemo extends UiApplication { private static int _interval = 5; private static int _cnt = 0; private EditField _status; private LocationProvider _locationProvider; private final class GPSDemoScreen extends MainScreen { protected void makeMenu(Menu menu, int instance) { menu.add( _close ); menu.addSeparator(); super.makeMenu(menu, instance); } public boolean onClose() { if ( _locationProvider != null ) { _locationProvider.reset(); _locationProvider.setLocationListener(null, -1, -1, -1); } return super.onClose(); } } public static void main(String[] args) { new GPSDemo().enterEventDispatcher(); } public GPSDemo() { GPSDemoScreen screen = new GPSDemoScreen(); screen.setTitle(new LabelField("GPS", LabelField.USE_ALL_WIDTH)); _status = new EditField(); screen.add(_status); startLocationUpdate(); pushScreen(screen); } private void updateLocationScreen(final String msg) { invokeLater(new Runnable() { public void run() { _status.setText(msg); short[] explodeAudio = { 300, 50, 500, 50, 300, 50, 500, 50, 300, 50 }; if (Alert.isBuzzerSupported()) Alert.startBuzzer(explodeAudio, 100); else if (Alert.isAudioSupported()) Alert.startAudio(explodeAudio,100); } }); } private MenuItem _close = new MenuItem("Close", 0, 10) { public void run() { System.exit(0); } }; private boolean startLocationUpdate() { boolean retval = false; try { _locationProvider = LocationProvider.getInstance(null); if ( _locationProvider == null ) { Runnable showGpsUnsupportedDialog = new Runnable() { public void run() { Dialog.alert("GPS is not supported on this platform, exiting..."); System.exit( 1 ); } }; invokeLater( showGpsUnsupportedDialog ); } else { _locationProvider.setLocationListener(new LocationListenerImpl(), _interval, 1, 1); retval = true; } } catch (LocationException le) { System.err.println("Failed to instantiate the LocationProvider object, exiting..."); System.err.println(le); System.exit(0); } return retval; } private static double round(double d, int decimal) { double powerOfTen = 1; while (decimal-- > 0) { powerOfTen *= 10.0; } double d1 = d * powerOfTen; int d1asint = (int)d1; double d2 = d1 - d1asint; return ( d2 >= 0.5 ? (d1asint + 1)/powerOfTen : (d1asint)/powerOfTen); } private class LocationListenerImpl implements LocationListener { public void locationUpdated(LocationProvider provider, Location location) { if(location.isValid()) { _cnt++; float heading = location.getCourse(); double longitude = location.getQualifiedCoordinates().getLongitude(); double latitude = location.getQualifiedCoordinates().getLatitude(); float altitude = location.getQualifiedCoordinates().getAltitude(); float speed = location.getSpeed(); StringBuffer sb = new StringBuffer(); sb.append("Long: "); sb.append(round(longitude,6)); sb.append("\n"); sb.append("Lat: "); sb.append(round(latitude,6)); sb.append("\n"); sb.append("Alt: "); sb.append(altitude); sb.append(" m"); sb.append("\n"); sb.append("North: "); sb.append(heading); sb.append("\n"); sb.append("Speed : "); sb.append(round(speed,2)); sb.append(" m/s"); sb.append("\n"); sb.append("Fixes : "); sb.append(_cnt); sb.append("\n"); GPSDemo.this.updateLocationScreen(sb.toString()); } } public void providerStateChanged(LocationProvider provider, int newState) { StringBuffer sb = new StringBuffer(); switch (newState) { case LocationProvider.AVAILABLE: sb.append("Provider AVAILABLE " + newState); break; case LocationProvider.OUT_OF_SERVICE: try { Thread.sleep(1000); } catch (Exception e) {} sb.append("Provider OUT_OF_SERVICE " + newState); provider.reset(); provider.setLocationListener(null, -1, -1, -1); provider.setLocationListener(new LocationListenerImpl(), _interval, 1, 1); break; case LocationProvider.TEMPORARILY_UNAVAILABLE: try { Thread.sleep(1000); } catch (Exception e) {} sb.append("Provider TEMPORARILY_UNAVAILABLE " + newState); provider.reset(); provider.setLocationListener(null, -1, -1, -1); provider.setLocationListener(new LocationListenerImpl(), _interval, 1, 1); break; } GPSDemo.this.updateLocationScreen(sb.toString()); } } }

 

 

 

Please use plain text.
BlackBerry Development Advisor
shaque
Posts: 228
Registered: ‎07-14-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

[ Edited ]

You are resetting the provider only once right after TEMPORARILY_UNAVAILABLE is triggered. Please note that my GPS module may not be back to coverage immediately after this event is triggered (depending on how fast I can run outdoors :smileyhappy: ). So essentially, your application needs to retry the reset logic every 5 minutes. You will also need to set the provider to null after you set the LocationListener to null (Use 0s instead of -1s) and obtain a new provider. Please see the post below for latest recommendations:

 

http://supportforums.blackberry.com/rim/board/message?board.id=java_dev&thread.id=744

Message Edited by shaque on 07-22-2008 04:16 PM
Please use plain text.
Developer
timnelson
Posts: 102
Registered: ‎07-15-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

Ok, I kind of get what you are saying.  Not sure why I have to set the provider to null, and recreate it, but I will modify the code and re-test. 

 

My original goal would be to use a TimerTask and do a one-shot getLocation on a brand new LocationProvider each time in the TimerTask, but alas in this code...once bluetooth is out of range and I come back range... I continue to get timeouts even though I am in range and using a new LocationProvider each time :-(   Strange enough, this code works fine on OS 4.5.0 :-(

Please use plain text.
BlackBerry Development Advisor
shaque
Posts: 228
Registered: ‎07-14-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

I am not sure if I understood it correctly. Did you mean the Bluetooth device going out of range from the BlackBerry or the GPS coverage is out of range (e.g. user is in an indoor environment)?
Please use plain text.
Developer
timnelson
Posts: 102
Registered: ‎07-15-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

I meant bluetooth out of range.  Simply turning the unit off for a few minutes and then turn it back on.  In either case (LocationListener or one-shot TimerTask with new LocationProvider each time) can never recover from this situation.  Like I said 4.5.0 (at least for one-shot scenario) _seems_ to work better.  I have seen numerous reports of bluetooth stack issues on 4.2.X and I wish I could get confirmation one way or the other from RIM.

 

I am going to post the paired-down one-shot TimerTask based code, since that is what my original J2ME application was based on and the one I hope to get to work.

 

Thanks for your help.

Please use plain text.
Developer
timnelson
Posts: 102
Registered: ‎07-15-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

Simple code (below) has a timer task every 60 seconds tries a one-shot getLocation on a new LocationProvider.   Again, once I turn off the bluetooth GPS, the location request times out.  Turn it back on and the application still keeps timing out.  Only clue I have found so far is that GoogleMaps (presumably) getting GPS fixes using the bluetooth SPP API works fine...even when this application continues to timeout. 

 

To revive it:

1. Starting and stopping the application _several_ times.

2. Running Google maps to hit bluetooth GPS

3. Sometimes I swear I need to do a hard reset (remove battery) to get it going!

 

Now debating whether I waste another 45 minutes re-installing OS 4.5.0 to prove that it will work there, or tracking down OS 4.1.? for the 8100 to see if the problem was introduced in 4.2.X. 

import net.rim.device.api.ui.*; import net.rim.device.api.ui.component.*; import net.rim.device.api.ui.container.*; import net.rim.device.api.system.*; import javax.microedition.location.*; import java.util.*; public class GPSDemo extends UiApplication { private static int _interval = 30; private static int _cnt = 0; private EditField _status; private Timer timer = null; private final class GPSDemoScreen extends MainScreen { protected void makeMenu(Menu menu, int instance) { menu.add( _close ); menu.add(_background); menu.addSeparator(); super.makeMenu(menu, instance); } public boolean onClose() { if (timer != null) timer.cancel(); return super.onClose(); } } public static void main(String[] args) { new GPSDemo().enterEventDispatcher(); } public GPSDemo() { GPSDemoScreen screen = new GPSDemoScreen(); screen.setTitle(new LabelField("GPS", LabelField.USE_ALL_WIDTH)); _status = new EditField(); screen.add(_status); pushScreen(screen); timer = new Timer(); timer.scheduleAtFixedRate(new GPSTask(),5000,60000); } private final class GPSTask extends TimerTask { public void run() { LocationProvider lp = null; try { Criteria cr = new Criteria(); lp = LocationProvider.getInstance(cr); Location l = lp.getLocation(30); if (l.isValid()) { Coordinates c = l.getQualifiedCoordinates(); if ( c != null ) { updateLocationScreen("Got a fix"); } else { updateLocationScreen("Coords was null"); } } else { updateLocationScreen("location not valid"); } } catch (Exception e) { updateLocationScreen("Failed: " + e.getMessage()); } if (lp != null) { lp.reset(); // Not sure if this is smart lp = null; } } } private void updateLocationScreen(final String msg) { invokeLater(new Runnable() { public void run() { _status.setText(msg); short[] explodeAudio = { 300, 50, 500, 50, 300, 50, 500, 50, 300, 50 }; if (Alert.isBuzzerSupported()) Alert.startBuzzer(explodeAudio, 100); else if (Alert.isAudioSupported()) Alert.startAudio(explodeAudio,100); } }); } private MenuItem _close = new MenuItem("Close", 0, 10) { public void run() { System.exit(0); } }; private MenuItem _background = new MenuItem("Background", 1, 10) { public void run() { requestBackground(); } }; }

 

Please use plain text.
Developer
timnelson
Posts: 102
Registered: ‎07-15-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

Ok, keeping this thread going...I installed OS 4.5.0 on my BB 8100 and the one-shot getLocation application posted WORKS correctly.  As long as the bluetooth GPS is out of range or off, the getLocation times out.  Once it is back in range the getLocation starts returning fixes again.  Can anyone test this on a version > 4.2.1 and not 4.5.0???  This is a real crisis when I'd like to release this application to my AT+T customer base, but unless I can get a BB 8100/8300 series that has a workable version of this OS I have a nightmare on my hands making each user upgrade to a new OS 4.5.0 and even worse a beta version (as far as I can tell) not blessed by the carrier.  As an aside, with 4.5.0 startAudio doesn't play the tone anymore...not sure why that is.
Please use plain text.
New Developer
edavis
Posts: 1
Registered: ‎07-25-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

Looking for help on setLocationListener hanging after a dozen or so successfull location(Using 8830 GPSDemo base code with numerous community changes) I stumbled accross this post. I implemented the timer/reset code in the second example and it seems to work OK. My question is what would be concidered the "best practice" around the BB GPS API for applications that would run in the background for extended periods. It seems like more of a hack to use the read/reset solution vs. threading the location listener.

 

Please use plain text.
Developer
timnelson
Posts: 102
Registered: ‎07-15-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

I wonder what OS you are running?  I've had weeks of problems getting bluetooth GPS going on 4.2.1.X.  Even some simple code that opens then closes a bluetooth port to the GPS will fail to connect often and then eventually say there are too many open connections.  I downgraded my Pearl to 4.2.0.X and things worked a bit better.  I got a Curve with 4.2.2.X today and the problem _seems_ to be fixed.  If you stare at the debugger with running bluetooth GPS on 4.2.1.X in an application that just uses a TimerTask to do a one-shot getLocation periodically, it fails and never comes back once the device goes off or out of range.  You can see in the debug output how they are forgetting to close the BT in their GPS code.  This must have been fixed in 4.2.2.X, cause I always see a close after I close the location provider.  I just wish RIM cared enough to tell me there are bluetooth issues on 4.2.1.X...believe me I've found hundreds of posts of people complaining about this.
Please use plain text.
Developer
peter_strange
Posts: 19,595
Registered: ‎07-14-2008
My Device: Not Specified

Re: Simple Bluetooth GPS code, could someone test?

I've just got my test 4.2.1 8100 back, and I have an external GPS puck I can test with.  Are you still looking for someone to try the code you posted?  Or are you happy that OS has problems connecting?

 

I can confirm that we have not had GPS location problems with 8800 devices running 4.2.1, which use their internal GPS, but have had with 8100s running 4.2.1.  Of course with the 8800 devices, the internal GPS can never go 'out of range'!

Please use plain text.