I’m working on a project that uses J2ME to display and interact with data from a remote server on handheld devices, specifically cellular phones. We are coding to the MIDP 1.0 specification, because that’s prevalent right now. The MIDP 2.0 will have some nice additions, and I’m looking forward to its widespread implementation. J2ME is nice because it has a lot of the same capabilities as java on the PC (J2SE). The specification states that J2ME is a strict subset of J2SE, that is, any class that is in the J2ME spec has to have all the methods of the J2SE class. The user interface of J2ME is also similar–there are forms, with various items that are added to them (choice groups, which are like radio buttons, and text fields are the main user input controls). In addition, a developer gets all the niceties of java–garbage collection.
While the transition from ‘normal’ web development (servlets, jsps) has been fairly painless, there have been a few hiccups. I wanted to cover some of them. This isn’t a colossal project, but we do have about 60 classes in 10 packages on the client communicating to ~150 classes on the server, so it’s not a stock ticker either.
Handheld devices, and particularly cell phones, are different than the browser. They are much more under the control of the folks who build the devices and install the initial software on them. If you thought it’s difficult to install the new JVM on your PC, try installing any kind of JVM on your cell phone. This means that the carrier (AT&T, Verizon, etc) matters in a fundamentally different manner than the OEM of your PC. This immediately jumps out when deciding on a platform. There are two main platforms out there for cell phones: BREW and J2ME. I don’t want to go into what BREW is here; Colin Fahey does a good job of covering the differences. Suffice it to say that, for both non technical and technical reasons, we decided to pass on BREW for a while. This means that Verizon, the largest US carrier, is off limits to us, as they only support BREW. We’re in the unenviable position of telling paying customers that they have to switch cell phone service if they want to use our app. Luckily, there’s hope for the future. J9 is a plug-in for BREW that will allow J2ME apps to run on BREW devices. However, it’s my understanding that we have to wait until BREW 2.0 is widely deployed to use this capability.
In addition to dealing with different support from different carriers (even with the same handset), developers of J2ME apps also have to deal with developing on a different platform. Only the foolish actually compile applications for a cell phone on a cell phone. They have slow processors, limited memory, no floating point support, etc. The MIDP 1.0 specification only requires you to have 128KB of memory and 8KB of persistent storage! This lack of resources means that you are going to cross compile: work and compile on your PC, download and test on your device. There are a couple of different solutions for this: IBM WebSphere Device Developer [WSDD] (which is based on Eclipse) and Sun’s Wireless Toolkit [WTK]. Each of these also provide an emulator so a developer is not continually downloading to their phone. I happen to have a non J2ME capable phone, so an emulator was a must for me. But, as ever, there are complications. Emulators aren’t perfect, as we discovered the first time we downloaded the application to a real phone. Our application makes a number of network hits to get information. This was working fine on IBM’s emulator, but when downloaded to the phone, the application locked up. After some investigation, it was determined that this was because the phone was asking for user permission to access the Internet, but our application wasn’t well enough behaved to let the phone have the system thread to ask the question. Luckily, this article set us straight. The Sun emulator was less forgiving. So, what I’ve ended up doing is using the ‘best of breed’ solution for each problem. I use vi to edit the source files, WSDD to compile and build that jad (WSDD makes it much easier than WTK), and the WTK emulator to test.
Information architecture is also a different beast on mobile devices. Rather than having 1024×768, 800×600, or 640×480 pixels, a developer has a 150×150 screen (of course, this depends wildly on the phone, but none of the phones I know of get anywhere close to the PC screen). This means that each piece of information must be carefully chosen. If there’s a ton of information, this also means that sometimes one has to break it up across screens. But, one should also minimize network hits and the amount of clicking around a user needs to do. Have you ever text messaged someone? Wasn’t entering text tedious? So, there’s this constant tension between having the application displaying useful information and minimizing the user input needed to get that information. Add to this the fact that we don’t really know how folks are going to use our device, and you have a coding headache. This article has some good suggestions. Of course, Jakob Nielsen has an answer–test it! Put it in front of some actual users and see what they do. And we will. But, when coding for a handheld device, I hold it as a general principle to minimize user input. In addition, there isn’t the nice MVC framework that I’ve grown used to. Instead of having an explicitly defined state machine, our application has a stack of previously visited screens. This works well currently, when information traversal is fairly linear (take me to the information I want!) but I’m leery of what will happen when the application grows more complex. Having each screen ‘know’ where it should go next doesn’t seem to scale very well.
Versioning for J2ME applications is new for me. It is similar to versioning for desktop applications, rather than web applications. I guess I’m spoiled–I’m used to being able to change the application at the server, and have those changes ripple out to all the dumb clients. J2ME is different–since you’re downloading a client to the user, changes to the server need to be coordinated with changes to the client. Not all changes, just those in the interface (which in our case is get parameters and XML over HTTP). But still, when you change that interface, you have four options: leave the old server up and running, break the older apps, have the features of the new server be a strict superset of the old one, or forcibly upgrade the older clients. This is a problem we haven’t faced yet, because we’re still in development. But, I can see it looming on the horizon. And as far as I can tell, this problem hasn’t been solved for the desktop (DLL hell, anyone), and they’ve had a heck of a lot more time and money to throw at it than I will.
The last concern about J2ME that I’m going to touch on today is performance. We haven’t gone through any kind of performance testing, and are still green enough to not have any experience that might guide us. So this section is just questions you should think about, rather than any kind of answers. There are several different types of performance, and they obviously aren’t orthogonal: number of threads, storage, memory, and network trips, and, perhaps most importantly, perceived. What are the limits on the number of threads on a mobile device? What is the cost of the context switches that happen? Should you keep a thread around, or dispose of it when you’re done? What should you store? How often should you verify it hasn’t changed on the server? MIDP 1.0 gives you the ability to store raw bytes–how do you want to abstract this for your application? What’s the speed of reading from ‘disk’? How much memory does your application use? Is it constant, or does it spike? How many new objects do you create? What’s the effect of this on the user experience? How many network trips do you make? What is this costing your user (both in dollars and in time)? How robust is it? What happens when you don’t have a crystal clear connection? How are you communicating with your server? How can you minimize your network connections? What feedback do you give a user when the device is waiting? What can you cache to speed up their experience?
J2ME is very cool, and I’m really enjoying learning more about it. As you can see from above, I’ve plenty to learn. There are several differences that you need to be aware of when doing mobile development in java, and I hope I’ve outlined some of them.