Displaying Nokia Maps in a Form in Java ME
This article shows how to use a map inside an LCDUI Form in Java ME.
Article Metadata
Code Example
Article
Contents |
Introduction
Applications that need to show maps within a Java ME Form cannot do so directly. This article shows how you can define a CustomItem (called MapCustomItem) which can be used to display a Nokia Map within a Form.
The article Creating a custom Map Item with Maps API for Java ME covers similar ground to this article, but uses a MapDisplay and MapFactory for the map. This article uses a MapCanvas, which saves you from having to implement methods for zooming, pan etc. You can create interactive map inside a Form with very little code.
Development
Nokia Maps for Java ME are displayed on a MapCanvas object. Unfortunately MapCanvas has some protected methods, which prevent it being used directly within a CustomItem. We therefore first create MapXtention, extending MapCanvas to provide public accessors for the required methods.
Finally, we then create a "Form ready" map item (MapCustomItem) by extending CustomItem (and using MapXtention).
MapXtention
MapXtention extends MapCanvas, creating public methods to access paint(), sizeChanged() and few other required methods of MapCanvas.
The new class contains these functions:
- public void paint(Graphics g);
- The definition of this function will be:
public void paint(Graphics g){
super.paint(g);
}
- public void size(int w, int h);
- This method is to re-size the MapCanvas to CustomItem size or desired size.
- The definition of this function will be:
public void size(int w, int h){
super.sizeChanged(w, h);
}
- public void onPressed(int x, int y);
- This method inter calls the MapCanvas pointerPressed() event method.
- The definition of this function will be:
public void onPressed(int x, int y){
super.pointerPressed(x, y);
}
- public void onDrag(int x, int y);
- This method inter calls the MapCanvas pointerDragged() event method.
- The definition of this function will be:
public void onDrag(int x, int y){
super.pointerDragged(x, y);
}
- public void onRelease(int x, int y);
- This method inter calls the MapCanvas pointerReleased() event method.
- The definition of this function will be:
public void onRelease(int x, int y){
super.pointerReleased(x, y);
}
The complete MapXtention is listed below:
import javax.microedition.lcdui.Display;
import javax.microedition.lcdui.Graphics;
import com.nokia.maps.map.MapCanvas;
public class MapXtention extends MapCanvas{
public MapXtention(Display arg0) {
super(arg0);
}
public void onMapContentComplete() {
}
public void onMapUpdateError(String arg0, Throwable arg1, boolean arg2) {
}
public void paint(Graphics g){
super.paint(g);
}
public void size(int w, int h){
super.sizeChanged(w, h);
}
public void onPressed(int x, int y){
super.pointerPressed(x, y);
}
public void onDrag(int x, int y){
super.pointerDragged(x, y);
}
public void onRelease(int x, int y){
super.pointerReleased(x, y);
}
}
MapCustomItem
MapCustomItem extends CustomItem and this is the class which performs necessary operations to make MapCanvas as CustomItem. The important methods that make MapCustomItem possible are:
- protected void paint(Graphics g, int w, int h);
- Abstract method from CustomItem class.
- It definition should be:
protected void paint(Graphics g, int w, int h) {
map.paint(g);
repaint();
}
- public void setMap(double lat, double lon, String title);
- This method can be used to set Map location, Zoom level and Pan. String title is an extra field, required only for creating StandardMarker, that use a String argument for displaying text with Marker.
- The definition of this method will be:
-
public void setMap(double lat, double lon, String title){
map.getMapDisplay().removeAllMapObjects();
map.getMapDisplay().reconnect();
//map.getMapDisplay().setCenter(new GeoCoordinate(lat, lon, 0));
map.getMapDisplay().setCenter(new GeoCoordinate(13.93436, 75.59581, 0));
map.getMapDisplay().setZoomLevel(17, 0, 0);
//map.getMapDisplay().addMapObject(map.getMapFactory().createStandardMarker(new GeoCoordinate(lat, lon, 0), 1, title, 2));
map.getMapDisplay().addMapObject(map.getMapFactory().createStandardMarker(new GeoCoordinate(13.93436, 75.59581, 0), 1, title, 2));
}
- double lat, double lon are the latitude and longitude value respectively.
Use MapCustomItem_Object.setMap( latitude_value, longitude_value, "Some text" ); in MIDlet/method to update/set map/map position and marker text. Frequent call to this method with changing position/location can be used for navigation/to map current position on map.
- Constructor should contain the following statements:
protected MapCustomItem(String title, Display d) {
super(title);
map = new MapXtention(d);
map.getMapDisplay().setBaseMapType(4);
map.size(getMinContentWidth(), getMinContentHeight());
}
- title: String representing title of the CustomItem (i.e title of MapCustomItem object in form).
- d: Display object, required by MapXtention object. However, MapXtention class extends MapCanvas class. MapXtention class also behaves exactly as MapCanvas class.
- setBaseMapType(4): 4 is the base type used forTransits as map display type. More.
- Set the size of map in the constructor only. Do not use this in paint method.
- Finally override pointerPressed(), pointerDragged() and pointerReleased() as shown bellow to perform Zooming, pan and other map operations.
protected void pointerPressed(int x, int y){
map.onPressed(x, y);
}
protected void pointerDragged(int x, int y){
map.onDrag(x, y);
}
protected void pointerReleased(int x, int y){
map.onRelease(x, y);
}
The complete MapCustomItem class is listed below:
import javax.microedition.lcdui.CustomItem;
import javax.microedition.lcdui.Display;
import javax.microedition.lcdui.Graphics;
import com.nokia.maps.common.GeoCoordinate;
public class MapCustomItem extends CustomItem{
MapXtention map;
protected MapCustomItem(String title, Display d) {
super(title);
map = new MapXtention(d);
map.getMapDisplay().setBaseMapType(4);
map.size(getMinContentWidth(), getMinContentHeight());
}
protected int getMinContentHeight() {
return 160;
}
protected int getMinContentWidth() {
return 210;
}
protected int getPrefContentHeight(int arg0) {
return getMinContentHeight();
}
protected int getPrefContentWidth(int arg0) {
return getMinContentWidth();
}
protected void paint(Graphics g, int w, int h) {
map.paint(g);
repaint();
}
public void setMap(double lat, double lon, String title){
map.getMapDisplay().removeAllMapObjects();
map.getMapDisplay().reconnect();
//map.getMapDisplay().setCenter(new GeoCoordinate(lat, lon, 0));
map.getMapDisplay().setCenter(new GeoCoordinate(13.93436, 75.59581, 0));
map.getMapDisplay().setZoomLevel(17, 0, 0);
//map.getMapDisplay().addMapObject(map.getMapFactory().createStandardMarker(new GeoCoordinate(lat, lon, 0), 1, title, 2));
map.getMapDisplay().addMapObject(map.getMapFactory().createStandardMarker(new GeoCoordinate(13.93436, 75.59581, 0), 1, title, 2));
}
protected void pointerPressed(int x, int y){
map.onPressed(x, y);
}
protected void pointerDragged(int x, int y){
map.onDrag(x, y);
}
protected void pointerReleased(int x, int y){
map.onRelease(x, y);
}
}
Tiny Map
You can create "tiny map" in form (these type of maps have zoom level set constant and user can pan the map). To create "tiny map", modify the following statement to these functions of MapCustomItem class.
protected int getMinContentHeight() {
return 60;
}
public void setMap(double lat, double lon, String title){
map.getMapDisplay().removeAllMapObjects();
map.getMapDisplay().reconnect();
map.getMapDisplay().removeMapComponent(map.getMapDisplay().getMapComponent("ZoomImgComponent")); //to remove Zoom Buttons
map.getMapDisplay().removeMapComponent(map.getMapDisplay().getMapComponent("DownloadIndicator")); //to remove download texts
// map.getMapDisplay().setCenter(new GeoCoordinate(lat, lon, 0));
map.getMapDisplay().setCenter(new GeoCoordinate(13.93436, 75.59581, 0));
map.getMapDisplay().setZoomLevel(17, 0, 0);
//map.getMapDisplay().addMapObject(map.getMapFactory().createStandardMarker(new GeoCoordinate(lat, lon, 0), 1, title, 2));
map.getMapDisplay().addMapObject(map.getMapFactory().createStandardMarker(new GeoCoordinate(13.93436, 75.59581, 0), 1, title, 2));
}






Contents
Hamishwillee - Excellent work! Subedited
Hi Adarsha,
As a document, this is VASTLY improved over your previous efforts: what you are trying to achieve is clear, and how to get there is explained logically. I cannot speak for the "technical content", but I would have said this was very useful.
I have subedited this and I suggest you have a look and check that you agree the changes are improvements. I believe so, but what you had was pretty good already! The main changes are:
The only thing that I think needs to change is the title. As for the Abstract, people who want to use Maps in a form will search/browse for a title that says something like that - not necessarily "MapCanvas" and CustomItem. I suggest you change the topic title to "Displaying Nokia Maps in a Form in Java ME"
Regards
Hamishhamishwillee 09:02, 10 August 2012 (EEST)
Adarsha saraff - Thanks
Hello Hamish,
Thanks for the edits....:)adarsha_saraff 12:38, 10 August 2012 (EEST)
Hamishwillee - Technical review
Technical reviewer says this is a good article, but unfortunately it repeats a lot of content in this article by Jappit: Creating a custom Map Item with Maps API for Java ME
This creates a static custom map item. It would be preference to using RESTful maps API since less downloading is involved. jappit’s article exposes an underlying MapDisplay which means the location, zoom and MapObjects can be added easily.
This function has a few issues:
I would change the signature to use GeoCoordinate – but this wouldn’t be an issue if it just exposed the MapDisplay anyway.
The only difference in the approach is whether the CustomItem should be based on a MapDisplay or a MapCanvas. Jappit’s uses the MapDisplay and hence doesn’t leave the standard MapComponents on screen. The new one uses MapCanvas and hence leaves half of an unusable zoom button on screen.
For the code as is, using the MapDisplay is preferred, since the Map is not interactive.
Other suggestions - if you update this code to expose a MapCanvas and get the canvas to respond to events then this would be something new. It would allow a user to interact with a small map on a Form.
As a minor suggestion
map.removeMapComponent(map.getMapComponent("ZoomImgComponent")); map.removeMapComponent(map.getMapComponent("DownloadIndicator"));Would get rid of the zoom button and number in the top right of the screen.hamishwillee 03:24, 13 August 2012 (EEST)
Adarsha saraff - Fixed it.
Thanks Hamish,
Didn't noticed existing article. But now I fixed it. Now user can perform all the map operations like Zoom in, Zoom out and pan.
public void setMap(double lat, double lon, String title){ map.getMapDisplay().removeAllMapObjects(); map.getMapDisplay().reconnect(); map.getMapDisplay().setCenter(new GeoCoordinate(lat, lon, 0)); map.getMapDisplay().setZoomLevel(4, 0, 0); map.getMapDisplay().addMapObject(map.getMapFactory().createStandardMarker(new GeoCoordinate(lat, lon, 0), 1, title, 2)); }This function is to demonstrate how you can set the map. It is not necessary that you need to use same statements as in above in setMap() method.
adarsha_saraff 14:51, 13 August 2012 (EEST)
Hamishwillee - Thanks!
Hi Adarsha
I've asked for further review, but looks like improvement to me! I've added a SeeAlso link to the related article.
In terms of previous suggestions you might want to "change the signature to use GeoCoordinate" rather than lon and lat.
In terms of "further improvements". Given that we know there is another way to do this, it is worth having a section outlining what it is that this method does compared to the other article, and why you might use this approach.
Regards
Hamishhamishwillee 04:57, 15 August 2012 (EEST)