Oracle ADF integration with Google Maps API3 – use cases
August 18th, 2011 | Posted by Dorin Simina in Oracle ADF | 5 Comments
Use case 1 – display route
Consider the following scenario: a route is composed by an ordered list of marker points saved in DB with information regarding name, latitude and longitude. For a selected route you want to display the map in a popup with a coloured route between the points which compose the route.
To resolve this issue, in your .jspx page you have to post the javascript code for displaying map with the route overlay. There are used 2 event properties:
- str - parse the marker points in the following format: latitude1;longitude1;name1~latitude2;longitude2;name2
- color - specify which color to use to display the route
<af:resource type="javascript"
source="http://maps.google.com/maps/api/js?sensor=false"/>
<af:resource type="javascript">
var map = null;
var stations = [];
var directionsDisplay = null;
var directionsService = null;
function initialize(evt) {
if(map === null){
var latlng = new google.maps.LatLng(62.01, -6.23);
var myOptions = {
zoom : 13, center : latlng, mapTypeId : google.maps.MapTypeId.ROADMAP
}
map = new google.maps.Map(document.getElementById("map"), myOptions);
directionsDisplay = new google.maps.DirectionsRenderer();
directionsDisplay.setMap(map);
directionsService = new google.maps.DirectionsService();
}
else {
for (i in stations)
{
stations[i].marker.setMap(null);
}
directionsDisplay.setMap(null);
}
var str = evt.getSource().getProperty("str");
var route_color = evt.getSource().getProperty("color");
var strokeColor;
if (route_color == "Red") {
strokeColor="#FF0000";
}
else if (route_color == "Green") {
strokeColor = "#00FF00";
}
else if (route_color == "Blue"){
strokeColor = "#0000FF";
}
else {
strokeColor = "#000000";
}
var array_stations = str.split(";");
var count = array_stations.length;
if (count > 0) {
var start_item = array_stations[0];
var items = start_item.split("~");
var startLatLng = new google.maps.LatLng(items[0], items[1]);
var sMarker = new google.maps.Marker( {
map : map, position : startLatLng, title : items[2]
});
stations.push({marker:sMarker});
var end_item = array_stations[count-2];
var itemsEnd = end_item.split("~");
var endLatLng = new google.maps.LatLng(itemsEnd[0], itemsEnd[1]);
var eMarker = new google.maps.Marker( {
map : map, position : endLatLng, title : itemsEnd[2]
});
stations.push({marker:eMarker});
var points = [];
for (var i=count-3; i>0; i--) {
var point_item = array_stations[i];
var itemsPoint = point_item.split("~");
var pointLatLng = new google.maps.LatLng(itemsPoint[0], itemsPoint[1]);
var iMarker = new google.maps.Marker( {
map : map, position : pointLatLng, title : itemsPoint[2]
});
stations.push({marker:iMarker});
points.push({location:pointLatLng, stopover: true});
}
var request = {
origin:startLatLng,
destination:endLatLng,
waypoints: points,
travelMode: google.maps.DirectionsTravelMode.DRIVING
};
directionsService.route(request, function (response, status) {
if (status == google.maps.DirectionsStatus.OK) {
directionsDisplay.setDirections(response);
directionsDisplay.setMap(map);
directionsDisplay.setOptions( {
suppressMarkers : true, polylineOptions : {
strokeColor : strokeColor, strokeOpacity : 0.8, strokeWeight : 7
}
});
}
else {
alert(status);
}
});
}
}
</af:resource>
And also in your popup place the following code (popup must have the property contentDelivery=”immediate”):
<div id="map" style="width: 500px; height: 500px"/>
Do not forget to add the clientAttribute options to load the values for the properties color and str:
<af:clientAttribute name="str"
value="#{row.StationsFormated}"/>
<af:clientAttribute name="color"
value="#{row.Color}"/>
Use case 2 – draggable markers
Consider the following scenario: you have a table displaying information about different map locations and when you select a row you are able to visualize the marker on map according to the current latitude and longitude. If you drag the displayed marker on map, the current row updates its latitude and longitude based on map events.
In your .jspx page you must declare the draggable marker script and the specific listener to update the table when the drag event is finished:
<af:document id="d1" clientComponent="true">
<af:serverListener type="mapClickListener"
method="#{pointBean.mapClick}"/>
<af:messages id="m1"/>
<f:facet name="metaContainer">
<trh:script id="s1" source="/js/citypulse.js"></trh:script>
<af:resource type="javascript"
source="http://maps.google.com/maps/api/js?sensor=false"/>
<af:resource type="javascript">
function initialize(evt) {
lng = evt.getSource().getProperty("long");
lat = evt.getSource().getProperty("lat");
var latlng = new google.maps.LatLng(lat, lng);
var myOptions = {
zoom : 16, center : latlng, mapTypeId : google.maps.MapTypeId.ROADMAP
}
var map = new google.maps.Map(document.getElementById("map"), myOptions);
var marker = new google.maps.Marker( {
map : map, position : latlng, draggable : true
});
google.maps.event.addListener(marker, "dragend", function () {
var point = marker.getPosition();
map.panTo(point);
var source = AdfPage.PAGE.findComponent("d1");
AdfCustomEvent.queue(source, "mapClickListener",
{
point_lat : point.lat(), point_lng : point.lng()
},
false);
});
}
</af:resource>
...
… and the bean method mapClick:
public void mapClick(ClientEvent clientEvent) {
logger.info("mapRightClick");
Map<String, Object> eventParams = clientEvent.getParameters();
Double lat = (Double)eventParams.get("point_lat");
Double lng = (Double)eventParams.get("point_lng");
Row currentRow = pointIt.getCurrentRow();
currentRow.setAttribute("Latitude", lat.toString());
currentRow.setAttribute("Longitude", lng.toString());
AdfFacesContext.getCurrentInstance().addPartialTarget(JSFUtils.findComponentInRoot("pointTable"));
}
Note: the presented sample codes are using Google Maps API 3.



Hi, great post!
But in my case is not working because this is always returning null:
document.getElementById(“map”)
I’ve place the div like this:
Can you help?
Thanks.
How have you placed the div?…you forgot to mention
Hi Simina,
I found that my problem was that I was calling the initialize() before the page loads, and that’s why the document.getElementById(“map”) returned null.
How can I call the initialize() method after the page load? I’m using jspx and I don’t have access to html body element..
Thanks.
Hi, yes. I’ve tried to paste the code here but it was removed :)
Can I send email with my jspx?
tks
Hi
You can setup var map = null before the definition of the initialize function.
Inside that function you can test if map == null…if yes make the initialization, and after the test place your business.
You can paste me the code at dorin.simina@gebs.ro and I’ll take a look.
Best regards,
Dorin