JavaFX location example with GPS

One of the cool things about the JavaFX Mobile platform running on myHTC Diamond phone, is the easy integration with GPS. In this article,I will describe the most simple example I could come up with.

I have been working with GPS integration in Java code since more than 10 yearsnow. In most cases, I had to use the serial io provided in comm.jarimplementations (the one providing javax.comm.SerialPort and others).Although this worked fine in most of the cases, theamount of low-level code was high compared with the amount of functionalcode.
I have been a big supporter of JSR 179, the Location API for J2ME. ThisAPI provides a simple way for obtaining locations and it also provides somecommon functionality (e.g. proximity listeners).Until recently, I haven’t seen much devices that contained a cleanimplementation of this API. But this is changing.

The JavaFX Mobile 1.2 for Windows Mobile platform contains an implementation ofJSR 179, and it works very well with JavaFX.
The following code example shows a simple JavaFX example showing the statusof the built-in GPS and the latest known position. It probably violates somepatterns, but the only goal is showing how you can obtain position inyour JavaFX programs.

The main class

The main class is a typical JavaFX example containing a Stage with aScene. The Scene contains 2 Text items. The contents of these text itemsare dynamically bound to some variables.

package com.lodgon.locationdemo;import javafx.stage.Stage;import javafx.scene.Scene;import javafx.scene.text.Text;import javafx.scene.text.Font;public var gpsStatus: String = "unknown";public var lat: Number = 0.0;public var lon: Number = 0.0;var stage: Stage = Stage {    title: "Location demo"    width: 250    height: 120    scene: Scene {        content: [            Text {                font : Font { size : 16 }                x: 10                y: 30                content: bind "gps status: {gpsStatus}"            },            Text {                font : Font { size : 16 }                x: 10                y: 50                content: bind "position: {lat}, {lon}"            }        ]    }}function run () {  stage;  var processor: LocationProcessor = LocationProcessor{};  processor.startReading();}

No magic in here, notice the LocationProcessor class thatwe instantiate and that will do the interaction with the GPS. Thisinstance will create a javax.microedition.location.LocationProviderand register a javax.microedition.location.LocationListenerwith it.

When the status of the GPS is changed, the providerStateChangedmethod is called. The new status is assigned to the gpsStatusvariable in the Main class and shown on the device screen.
Similarly, when a new position is detected, the locationUpdatemethod is called, and the lat and lon variablesin the Main class are changed.

package com.lodgon.locationdemo;import javax.microedition.location.LocationListener;import javax.microedition.location.Location;import javax.microedition.location.LocationProvider;import javax.microedition.location.QualifiedCoordinates;public class LocationProcessor extends LocationListener  {  var provider: LocationProvider;  public function startReading() {    provider = LocationProvider.getInstance(null);    provider.setLocationListener(this, 10, 5, -1);    providerStateChanged (provider, provider.getState());  }  override function locationUpdated(provider: LocationProvider, location: Location) {    if (location != null) {      var coords: QualifiedCoordinates = location.getQualifiedCoordinates();      if (coords != null) {        var lat = coords.getLatitude();        var lon = coords.getLongitude();        println ("[JVDBG] lat = {lat}");        Main.lat = lat;        Main.lon = lon;      }    }  }  override function providerStateChanged(provider: LocationProvider, stat: Integer) {    if (stat == 1) {      Main.gpsStatus = "Available";    }    if (stat == 2) {      Main.gpsStatus = "Temporarily Unvailable";    }    if (stat == 3) {      Main.gpsStatus = "Out Of Service";    }  }}

For more information about JSR 179, see theJavadoc pages. You can easily change the update frequency (currently 10 seconds),timeout (currently 5 seconds), and other criteria.Also note that we actually should not do any processing in the interfacecallback methods. Since this is a simple example without much processing,I didn’t use the javafx async threading mechanism for simplicity.

Social Networking in Telematics

I'm on my way back from the ITS 2009 world conference in Stockholm — see the website of the World Contress and Exhibition on Intelligent Transport Systems and Services for more information about this conference. We were showcasing an application that combines social networking with vehicle telematics. The past few days were really exhausting, but it definitely was worth it.

Our company LodgON was selected as one of the four finalists of the CVIS Application Contest. CVIS is a project funded by the European Commission. In this project, a global architecture is defined that allows the creation of cooperative vehicle applications. Developers use the Service Development Kit, based on the OSGi software of MakeWave and create their own applications.

The four finalists developed different applications, ranging from pedestrian safety over intelligent agents to the social networking application that we developed. Visitors of the CVIS booth could vote for one of the finalists. We won the silver prize, worth 15.000 EUR. I am happy because we won this prize, and I am unhappy since we didn't win the gold prize (25.000 EUR).

For LodgON, this conference was also very important since we demonstrated our Dali-based vehicle social networking application. You can find more information about this application at our website. We have a strong background in Social Networking, and most of the LodgON employees also have a background in Telematics. This combination automatically leads to a Social Networking application for telematics. My main question, though, was if the automotive industry was ready for this kind of applications. I am extremely pleasant surprised that indeed there was a huge interest from conference visitors in our application. Road authorities, car OEM's, telecom operators, consumer organisations,… they all showed a clear interest in Social Networking, and they definitely do realize the benefits of social networking if it is properly implemented.

With our Social CVIS application, we showed that the research and development we have done during the past years in the field of social networking is really rewarding. We know the ins and outs, the benefits and pittfalls. We realize the importance of social status, we balance between clarity and fine-grained permission models. Social networking is more than having an account on facebook. The return on investment can be huge, but your project can also fail completely if you don't combine users expectations with the goals of the company/organisation that is behind the project.
We will have some work in the coming weeks, with the follow-up of the new contacts we have (and the re-connection with some old friends). But there are lots of opportunities out there now.

From a technical point of view (and in the end, that is what I am mostly involved with), this project has been fun as well. We combined our experience with OSGi, Glassfish and JavaFX in order to create the prototype. Glassfish is really mature, and more than ready for production. We already knew this, but it's proven once again. The ease of development and the clear way of operations is worth a lot. The Jersey bundle in Glassfish (yes, we talk bundles since we use Glassfish v3) is one of my favourites, it allows an uncoupled REST-based client-server approach.
We showed 4 clients for our application, one of them being a JavaFX mobile client, using GPS data through JSR 179. I have been working with GPS data often, and in most cases it came down to using the serial COMM port and talking to native GPS drivers. Which is fun for a while. I was extremely happy and positively surprised when I discovered that JavaFX supports JSR 179, and it takes about 10 lines of code in order to read the exact position from my HTC Diamond phone. This is one of the reasons I believe in JavaFX: easy support for real devices.

The telematics, location based social networking server is based on our Dali Community Server. We announced our Dali Roadmap last week as well, and the positive feedback we got about this application proved to me that we made the right decisions in the development of Dali.

JavaFX chat client with Comet server

I have written a few entries about a JavaFX chat client and about a Comet Chat engine. Now, I have put together the simplest examples I could come up with.

Both the ChatServer (using Comet) and the ChatClient (in JavaFX) can be downloaded here.
Some remarks:

Comet based ChatServer

The ChatServer directory contains a Netbeans project that uses Comet in GlassFish v2. If you want to run this example in GlassFish v3, you have to change the package name com.sun.enterprise.web.connector.grizzly.comet; into com.sun.grizzly.comet.CometContext . The ChatServer contains 3 classes:

ChatEntry

This is a POJO, containing the information about chat entries (only a username and a text are used).

ChatServlet

This is the entry point for clients. Comet initialization is done in the init(ServletConfig config) method. Incoming requests have a parameter method. This parameter can have two values: listen and chat.

listen

A new CometHandler is created, and the PrintWriter of the HttpServletResponse is attached to the CometContext When new chat entries are received, the CometHandler will send the content to the attached writer.

chat

An incoming chat entry is received. The CometContext is notified about this event, and it will send the chat text to all registered listeners.

ChatHandler

This is our implementation of the CometHandler. When a client starts listening, a new instance of the ChatHandler is created, and the PrintWriter connected to the ServletResponse is stored. When new chat entries are received, the onEvent method will be called, and the chat text will be written to the PrintWriter instance.

 

JavaFX ChatClient

The ChatClient is slightly more complicated. See one of my previous blog entries for a detailed description of a JavaFX chat client. The example described in today's entry is simplified a bit. We don't use a separate class for writing new chat entries, but we use the HttpRequest for calling a url containing the chat entry information. We can't use the same approach for reading incoming chat entries, since the onInput function of the HttpRequest is only called when all input has been read. The existing javafx.data packages are very suitable for reading message-based content (i.e. RSS feeds), but not for streaming. Hence, we created a mechanism where a callback interface (ChatInput is called each time the InputStream receives a new chat entry). This is done by means of the FXReader JavaFX class and the AsyncReader java class. Again, for implementation details have a look at my previous blog entry.

 

At LodgON, we are working on a product that contains chat functionality. It is more complex than the example we've shown here, i.e. the chat can be moderated, users can have different roles, documents can be shown,… . The basic principles of the chat interactions are the same, though.