/**
** Copyright (c) 2010 Ushahidi Inc
** All rights reserved
** Contact: team@ushahidi.com
** Website: http://www.ushahidi.com
**
** GNU Lesser General Public License Usage
** This file may be used under the terms of the GNU Lesser
** General Public License version 3 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 3 requirements
** will be met: http://www.gnu.org/licenses/lgpl.html.
**
**
** If you have questions regarding the use of this file, please contact
** Ushahidi developers at team@ushahidi.com.
**
**/
package com.ushahidi.android.app.fragments;
import java.util.ArrayList;
import java.util.List;
import android.app.Dialog;
import android.content.DialogInterface;
import android.os.Bundle;
import android.support.v4.app.DialogFragment;
import android.text.TextUtils;
import android.widget.Toast;
import com.actionbarsherlock.view.Menu;
import com.actionbarsherlock.view.MenuInflater;
import com.google.android.gms.common.ConnectionResult;
import com.google.android.gms.common.GooglePlayServicesUtil;
import com.google.android.gms.maps.CameraUpdate;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.model.BitmapDescriptorFactory;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.LatLngBounds;
import com.google.android.gms.maps.model.MarkerOptions;
import com.ushahidi.android.app.R;
import com.ushahidi.android.app.util.Util;
/**
* @author eyedol
*/
public abstract class BaseMapFragment extends SherlockMapFragment {
protected GoogleMap map;
protected UpdatableMarker updatableMarker;
protected static final String TAG_ERROR_DIALOG_FRAGMENT = "errorDialog";
/**
* Menu resource id
*/
protected final int menu;
/**
* BaseActivity
*
* @param menu menu resource id
*/
public BaseMapFragment(int menu) {
this.menu = menu;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
setHasOptionsMenu(true);
// GoogleMapOptions op = new GoogleMapOptions();
// op.zOrderOnTop(true);
// newInstance(op);
}
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
if (this.menu != 0) {
inflater.inflate(this.menu, menu);
}
}
@Override
public boolean onContextItemSelected(android.view.MenuItem item) {
return super.onContextItemSelected(item);
}
protected void updateMarker(double latitude, double longitude,
boolean center) {
updateMarker(getPoint(latitude, longitude), center);
}
/**
* Convert latitude and longitude to a GeoPoint
*
* @param latitude Latitude
* @param longitude Lingitude
* @return GeoPoint
*/
protected LatLng getPoint(double latitude, double longitude) {
return (new LatLng(latitude, longitude));
}
protected void updateMarker(LatLng point, boolean center) {
if (map != null) {
if (updatableMarker == null) {
CameraUpdate p = CameraUpdateFactory.newLatLng(point);
map.moveCamera(p);
updatableMarker = createUpdatableMarker(point);
} else {
updatableMarker.update(point);
}
if (center) {
CameraUpdate c = CameraUpdateFactory.newLatLng(point);
map.moveCamera(c);
}
CameraUpdate zoom = CameraUpdateFactory.zoomTo(15);
map.animateCamera(zoom);
map.getUiSettings().setZoomControlsEnabled(false);
}
}
/* Override this to set a custom marker */
protected UpdatableMarker createUpdatableMarker(LatLng point) {
return new MapMarker(point);
}
/* Override this to set a custom marker */
protected UpdatableMarker createUpdatableMarker() {
return new MapMarker();
}
protected void createMarker(double lat, double lng, String title,
String snippet) {
if (map != null) {
MapMarker marker = new MapMarker();
marker.addMarker(map, lat, lng, title, snippet);
}
}
protected void createMarker(double lat, double lng, String title,
String snippet, String fileName) {
if (map != null) {
MapMarker marker = new MapMarker();
marker.addMarkerWithIcon(map, lat, lng, title, snippet, fileName);
}
}
/**
* Check if Google Maps exist on the device
*
* @return
*/
protected boolean checkForGMap() {
int status = GooglePlayServicesUtil
.isGooglePlayServicesAvailable(getActivity());
if (status == ConnectionResult.SUCCESS) {
return (true);
} else if (GooglePlayServicesUtil.isUserRecoverableError(status)) {
ErrorDialogFragment.newInstance(status).show(
getActivity().getSupportFragmentManager(),
TAG_ERROR_DIALOG_FRAGMENT);
} else {
Util.showToast(getActivity(), R.string.no_maps);
getActivity().finish();
}
return false;
}
private class MapMarker implements UpdatableMarker {
public MapMarker(LatLng point) {
update(point);
}
public MapMarker() {
}
public LatLng getCenter(double lat, double lng) {
LatLngBounds bounds = new LatLngBounds.Builder().include(
new LatLng(lat, lng)).build();
return Util.getCenter(bounds);
}
public void update(LatLng point) {
if (point != null) {
map.addMarker(new MarkerOptions().position(point));
}
}
public void addMarker(GoogleMap map, final double lat, final double lng,
String title, String snippet) {
final LatLng latLng = new LatLng(lat, lng);
markersHolder.add(title);
map.addMarker(new MarkerOptions().position(latLng).title(title)
.snippet(snippet));
}
public void addMarkerWithIcon(GoogleMap map, final double lat, final double lng,
String title, String snippet, String filename) {
final LatLng latLng = new LatLng(lat, lng);
// FIX ME: Using the title to find which latlng have been tapped.
// This ugly hack has to do with the limitation in Google maps api
// for android
// SEE:
// https://code.google.com/p/gmaps-api-issues/issues/detail?id=4650
markersHolder.add(title);
if ((filename != null) && (!TextUtils.isEmpty(filename))) {
map.addMarker(new MarkerOptions().position(latLng)
.title(title).snippet(snippet)
.icon(BitmapDescriptorFactory.fromPath(filename)));
} else {
map.addMarker(new MarkerOptions().position(latLng)
.title(title).snippet(snippet));
}
}
public void clearMapMarkers() {
if (map != null && markersHolder != null) {
markersHolder.clear();
map.clear();
}
}
}
public static class ErrorDialogFragment extends DialogFragment {
static final String ARG_STATUS = "status";
static ErrorDialogFragment newInstance(int status) {
Bundle args = new Bundle();
args.putInt(ARG_STATUS, status);
ErrorDialogFragment result = new ErrorDialogFragment();
result.setArguments(args);
return (result);
}
@Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
Bundle args = getArguments();
return GooglePlayServicesUtil.getErrorDialog(
args.getInt(ARG_STATUS), getActivity(), 0);
}
@Override
public void onDismiss(DialogInterface dlg) {
if (getActivity() != null) {
getActivity().finish();
}
}
}
public abstract interface UpdatableMarker {
// This is for a workaround regarding this issue
// https://code.google.com/p/gmaps-api-issues/issues/detail?id=4650
public List<String> markersHolder = new ArrayList<String>();
public abstract void update(LatLng point);
public abstract void addMarker(GoogleMap map, double lat, double lng,
String title, String snippet);
public abstract void addMarkerWithIcon(GoogleMap map, double lat,
double lng, String title, String snippet, String filename);
public abstract LatLng getCenter(double lat, double lng);
public abstract void clearMapMarkers();
}
protected void log(String message) {
new Util().log(message);
}
protected void log(String format, Object... args) {
new Util().log(String.format(format, args));
}
protected void log(String message, Exception ex) {
new Util().log(message, ex);
}
protected void toastLong(String message) {
Toast.makeText(getActivity(), message, Toast.LENGTH_LONG).show();
}
protected void toastLong(int message) {
Toast.makeText(getActivity(), getText(message), Toast.LENGTH_LONG)
.show();
}
protected void toastLong(String format, Object... args) {
Toast.makeText(getActivity(), String.format(format, args),
Toast.LENGTH_LONG).show();
}
protected void toastLong(CharSequence message) {
Toast.makeText(getActivity(), message.toString(), Toast.LENGTH_LONG)
.show();
}
protected void toastShort(String message) {
Toast.makeText(getActivity(), message, Toast.LENGTH_SHORT).show();
}
protected void toastShort(String format, Object... args) {
Toast.makeText(getActivity(), String.format(format, args),
Toast.LENGTH_SHORT).show();
}
protected void toastShort(int message) {
Toast.makeText(getActivity(), getActivity().getString(message),
Toast.LENGTH_SHORT).show();
}
protected void toastShort(CharSequence message) {
Toast.makeText(getActivity(), message.toString(), Toast.LENGTH_SHORT)
.show();
}
}