package org.tipple.mapDisplay; import java.io.File; import java.text.DecimalFormat; import java.util.ArrayList; import java.util.HashMap; import java.util.HashSet; import java.util.Set; import org.mapsforge.android.maps.ArrayItemizedMarkerOverlay; import org.mapsforge.android.maps.CircleOverlay; import org.mapsforge.android.maps.GeoPoint; import org.mapsforge.android.maps.MapController; import org.mapsforge.android.maps.MapView; import org.mapsforge.android.maps.OverlayMarkerItem; import org.mapsforge.android.maps.OverlayTextAudioItem; import org.mapsforge.android.maps.Projection; import android.app.Activity; import android.content.Context; import android.graphics.Color; import android.graphics.Paint; import android.graphics.Point; import android.graphics.drawable.Drawable; import android.location.Location; import android.location.LocationListener; import android.location.LocationManager; import android.media.MediaPlayer; import android.os.Bundle; import android.os.Vibrator; import android.widget.TextView; public class locationListener implements LocationListener { public static Location lastKnownLocation = null; protected ArrayList locations; protected ArrayList locations_; Drawable highlight_marker2; Drawable highlight_marker1; Drawable marker; protected Activity activity_; protected MapView map_view_; protected TextView text_view_; protected LocationManager tip_location_manager_; protected TippleLocationManagerVersion2 tipManager; // protected tippleLocationManager tipManager; protected MapController map_controller_; protected CircleOverlay here_overlay_; protected ArrayItemizedMarkerOverlay highlight_marker_overlay_; protected Vibrator vibrator_; protected Set curr_locations_; protected Set prev_locations_; HashMap highlight_marker_hash_; public locationListener(Activity activity, MapView map_view, TextView text_view, LocationManager location_manager, TippleLocationManagerVersion2 tipManager, ArrayList locations) { activity_ = activity; map_view_ = map_view; text_view_ = text_view; this.tipManager = tipManager; tip_location_manager_ = location_manager; locations_ = locations; // location aware Paint circleFillPaint = new Paint(Paint.ANTI_ALIAS_FLAG); circleFillPaint.setStyle(Paint.Style.FILL); circleFillPaint.setColor(Color.GREEN); circleFillPaint.setAlpha(64); Paint circleOutlinePaint = new Paint(Paint.ANTI_ALIAS_FLAG); circleOutlinePaint.setStyle(Paint.Style.STROKE); circleOutlinePaint.setColor(Color.GREEN); circleOutlinePaint.setAlpha(128); circleOutlinePaint.setStrokeWidth(3); Drawable highlightMarker = activity_.getResources().getDrawable( R.drawable.markerhighlightbook1); highlight_marker_overlay_ = new ArrayItemizedMarkerOverlay( highlightMarker, activity); map_view_.getOverlays().add(highlight_marker_overlay_); vibrator_ = (Vibrator) activity .getSystemService(Context.VIBRATOR_SERVICE); curr_locations_ = new HashSet(); prev_locations_ = new HashSet(); highlight_marker_hash_ = new HashMap(); } ArrayList getLocations() { return locations_; } void setLocations(ArrayList locations) { this.locations_ = locations; } Activity getActivity() { return activity_; } void resetOverlayThreadsOnListener() { if (highlight_marker_overlay_ != null) { highlight_marker_overlay_.clear(); highlight_marker_overlay_ = null; } if (highlight_marker_hash_ != null) { highlight_marker_hash_.clear(); highlight_marker_hash_ = null; } if (locations_ != null) { locations_.clear(); locations_ = null; } if (curr_locations_ != null) { curr_locations_.clear(); curr_locations_ = null; } if (prev_locations_ != null) { prev_locations_.clear(); prev_locations_ = null; } } boolean checking_location_ = false; synchronized protected boolean getLock() { if (!checking_location_) { checking_location_ = true; } return checking_location_; } synchronized protected void freeLock() { checking_location_ = false; } protected double pointDistance(Point place_point, Point here_point) { double delta_x = place_point.x - here_point.x; double delta_y = place_point.y - here_point.y; double pixel_distance = Math.sqrt((delta_x * delta_x) + (delta_y * delta_y)); return pixel_distance; } Point lastLoggedPoint_ = null; protected void updateActiveLocations(Location loc) { // Find out if the current GPS location lies within the boundaries // of any of the tour locations Projection projection = map_view_.getProjection(); byte zoom_level = map_view_.getZoomLevel(); // byte zoom_level = 10; // work at a reasonable level of scale float in_out_gap_meters = 3.0f; float in_out_gap_pixels = projection.metersToPixels(in_out_gap_meters, zoom_level); double here_latitude = loc.getLatitude(); double here_longitude = loc.getLongitude(); GeoPoint here_geopoint = new GeoPoint(here_latitude, here_longitude); Point here_point = projection.toPoint(here_geopoint, null, zoom_level); if (lastLoggedPoint_ == null) { lastLoggedPoint_ = here_point; // tippleActivity.log.optMessage("GPS Location Reading"); } else { float far_enough_meters = 3.0f; // 3 meters float far_enough_pixels = projection.metersToPixels( far_enough_meters, zoom_level); if (pointDistance(here_point, lastLoggedPoint_) > far_enough_pixels) { // tippleActivity.log.optMessage("GPS Location Reading"); } } for (int i = 0; i < locations_.size(); i++) { tippleLocation place = locations_.get(i); double place_latitude = place.getlatitude(); double place_longitude = place.getlongitude(); double radius_meters = place.getradius() * 1000.0; GeoPoint place_geopoint = new GeoPoint(place_latitude, place_longitude); Point place_point = projection.toPoint(place_geopoint, null, zoom_level); float radius_pixel_distance = projection.metersToPixels( (float) radius_meters, zoom_level); double delta_x = place_point.x - here_point.x; double delta_y = place_point.y - here_point.y; double pixel_distance = Math.sqrt((delta_x * delta_x) + (delta_y * delta_y)); double outside_pixel_distance = radius_pixel_distance + in_out_gap_pixels; double inside_pixel_distance = radius_pixel_distance; if (pixel_distance <= inside_pixel_distance) { if (!curr_locations_.contains(place)) { // User has entered new location on tour curr_locations_.add(place); vibrator_.vibrate(1000); Bundle bundle = new Bundle(); bundle.putString("placeName", place.getTitle()); boolean visited_previously = prev_locations_ .contains(place); tipManager .textToSpeechToLocation(place, visited_previously); OverlayTextAudioItem here_marker_item = (OverlayTextAudioItem) TippleLocationManagerVersion2.itemizedMarkerOverlayArrayList .get(i); GeoPoint dm_geopoint = here_marker_item.getPoint(); String title = here_marker_item.getTitle(); String[] nodeId = here_marker_item.getNodeID().split("\\."); if (nodeId[0] .equalsIgnoreCase(TippleLocationManagerVersion2.stationOfCrossURL)) {// hamiltonGardenURL marker = activity_.getResources().getDrawable( R.drawable.markerhighlightbook2); } else { marker = activity_.getResources().getDrawable( R.drawable.markerhighlightbook1);// red+yellow } OverlayMarkerItem highlight_marker_item = new OverlayMarkerItem( dm_geopoint, title); highlight_marker_item.setMarker(marker); highlight_marker_hash_.put(i, highlight_marker_item); highlight_marker_overlay_.addOverlay(highlight_marker_item); try { // Cue up audio alert String audio_dir = "/sdcard/";// currently all file // String audio_dir = tippleActivity.audioDirectory; File alert_file = new File(audio_dir, "BeepMorseSonar.wav"); String alert_filename = alert_file.getAbsolutePath(); MediaPlayer mp = new MediaPlayer(); mp.setDataSource(alert_filename); mp.prepare(); mp.start(); } catch (Exception e) { System.err .println("Failed to play audio alert for active GPS location"); e.printStackTrace(); } // Now record the fact we've been here prev_locations_.add(place); } } else if (pixel_distance >= outside_pixel_distance) { if (curr_locations_.contains(place)) { curr_locations_.remove(place); OverlayMarkerItem highlight_marker_item = highlight_marker_hash_ .remove(i); highlight_marker_overlay_ .removeOverlay(highlight_marker_item); } } } } public void onLocationChanged(Location loc) { if (loc != null) { System.err .println("TipLocationListener::onLocationChaged -- start"); lastKnownLocation = loc; if (getLock()) { updateActiveLocations(loc); freeLock(); } DecimalFormat truncPlaces = new DecimalFormat("0.00000"); double longitude = loc.getLongitude(); double latitude = loc.getLatitude(); String trunc_long = truncPlaces.format(longitude); String trunc_lat = truncPlaces.format(latitude); String text_mess = "(Long,Lat): (" + trunc_long + "," + trunc_lat + ")"; text_view_.setText(text_mess); // location aware GeoPoint point = new GeoPoint(latitude, longitude); // Use the following line if you want to map to auto center on the // GPS location boolean centre_on_gps_loc = tippleActivity.sharedPreferences .getBoolean("centreOnGPSLoc", false); if (centre_on_gps_loc) { MapController map_controller = map_view_.getController(); if (map_controller != null) { map_controller.setCenter(point); } } } // System.err.println("TipLocationListener::onLocationChaged -- finished"); } @Override public void onProviderDisabled(String provider) { // TODO Auto-generated method stub System.err.println("TipLocationListener::onProviderDisabled()"); } @Override public void onProviderEnabled(String provider) { // TODO Auto-generated method stub System.err.println("TipLocationListener::onProviderEnabled()"); } @Override public void onStatusChanged(String provider, int status, Bundle extras) { // TODO Auto-generated method stub System.err.println("TipLocationListener::onStatusChanged()"); } }