From 558777919e335328e12cd9fdfee8558141a165a6 Mon Sep 17 00:00:00 2001 From: Taranenko Roman Date: Thu, 30 Oct 2014 22:30:14 +0200 Subject: [PATCH 1/2] Turn on the screen for a few seconds when there is a voice prompt --- OsmAnd/AndroidManifest.xml | 1 + .../src/net/osmand/plus/OsmandSettings.java | 2 + .../osmand/plus/activities/MapActivity.java | 63 +++++++++++++- .../net/osmand/plus/routing/VoiceRouter.java | 82 +++++++++++++++++++ 4 files changed, 147 insertions(+), 1 deletion(-) diff --git a/OsmAnd/AndroidManifest.xml b/OsmAnd/AndroidManifest.xml index 8020a1ae85..7e6fb57f37 100644 --- a/OsmAnd/AndroidManifest.xml +++ b/OsmAnd/AndroidManifest.xml @@ -10,6 +10,7 @@ + diff --git a/OsmAnd/src/net/osmand/plus/OsmandSettings.java b/OsmAnd/src/net/osmand/plus/OsmandSettings.java index 0383c1a0f4..ea25e90e19 100644 --- a/OsmAnd/src/net/osmand/plus/OsmandSettings.java +++ b/OsmAnd/src/net/osmand/plus/OsmandSettings.java @@ -988,6 +988,8 @@ public class OsmandSettings { public CommonPreference PREVIOUS_INSTALLED_VERSION = new StringPreference("previous_installed_version", "").makeGlobal(); + public CommonPreference WAKE_ON_VOICE = new BooleanPreference("wake_on_voice", true).makeGlobal(); + public ITileSource getMapTileSource(boolean warnWhenSelected) { String tileName = MAP_TILE_SOURCES.get(); diff --git a/OsmAnd/src/net/osmand/plus/activities/MapActivity.java b/OsmAnd/src/net/osmand/plus/activities/MapActivity.java index 03d1cc8ce0..74f50a554d 100644 --- a/OsmAnd/src/net/osmand/plus/activities/MapActivity.java +++ b/OsmAnd/src/net/osmand/plus/activities/MapActivity.java @@ -39,6 +39,7 @@ import net.osmand.plus.render.RendererRegistry; import net.osmand.plus.resources.ResourceManager; import net.osmand.plus.routing.RoutingHelper; import net.osmand.plus.routing.RoutingHelper.RouteCalculationProgressCallback; +import net.osmand.plus.routing.VoiceRouter; import net.osmand.plus.views.AnimateDraggingMapThread; import net.osmand.plus.views.OsmAndMapLayersView; import net.osmand.plus.views.OsmAndMapSurfaceView; @@ -48,6 +49,7 @@ import net.osmand.plus.views.corenative.NativeQtLibrary; import net.osmand.render.RenderingRulesStorage; import net.osmand.util.Algorithms; import android.app.Dialog; +import android.app.KeyguardManager; import android.app.Notification; import android.app.NotificationManager; import android.app.PendingIntent; @@ -62,7 +64,9 @@ import android.os.Bundle; import android.os.Environment; import android.os.Handler; import android.os.Message; +import android.os.PowerManager; import android.util.DisplayMetrics; +import android.util.Log; import android.view.Gravity; import android.view.KeyEvent; import android.view.MotionEvent; @@ -74,11 +78,13 @@ import android.widget.FrameLayout; import android.widget.ProgressBar; import android.widget.Toast; -public class MapActivity extends AccessibleActivity { +public class MapActivity extends AccessibleActivity implements + VoiceRouter.VoiceMessageListener { private static final int SHOW_POSITION_MSG_ID = OsmAndConstants.UI_HANDLER_MAP_VIEW + 1; private static final int LONG_KEYPRESS_MSG_ID = OsmAndConstants.UI_HANDLER_MAP_VIEW + 2; private static final int LONG_KEYPRESS_DELAY = 500; + private static final int WAKE_ON_VOICE_INTERVAL = 10000; // 10 seconds private static MapViewTrackingUtilities mapViewTrackingUtilities; @@ -106,6 +112,9 @@ public class MapActivity extends AccessibleActivity { private StateChangedListener applicationModeListener; private FrameLayout lockView; private GpxImportHelper gpxImportHelper; + private Long lastWakeOnTime = 0l; + private PowerManager.WakeLock wakeLock = null; + private KeyguardManager.KeyguardLock keyguardLock = null; private Notification getNotification() { @@ -283,6 +292,9 @@ public class MapActivity extends AccessibleActivity { @Override protected void onResume() { super.onResume(); + if ((wakeLock != null) || (keyguardLock != null)) { + return; + } cancelNotification(); //fixing bug with action bar appearing on android 2.3.3 if (getSupportActionBar() != null){ @@ -524,6 +536,10 @@ public class MapActivity extends AccessibleActivity { @Override protected void onStart() { super.onStart(); + if ((wakeLock == null) || (keyguardLock == null)) { + VoiceRouter voiceRouter = app.getRoutingHelper().getVoiceRouter(); + voiceRouter.removeVoiceMessageListener(this); + } } protected void setProgressDlg(Dialog progressDlg) { @@ -546,6 +562,10 @@ public class MapActivity extends AccessibleActivity { progressDlg.dismiss(); progressDlg = null; } + if (!isFinishing()) { + VoiceRouter voiceRouter = app.getRoutingHelper().getVoiceRouter(); + voiceRouter.addVoiceMessageListener(this); + } super.onStop(); } @@ -759,4 +779,45 @@ public class MapActivity extends AccessibleActivity { public View getLayout() { return getWindow().getDecorView().findViewById(android.R.id.content); } + + @Override + public void onVoiceMessage() { + if (settings.WAKE_ON_VOICE.get()) { + lastWakeOnTime = System.currentTimeMillis(); + if (wakeLock == null) { + PowerManager pm = (PowerManager) getSystemService(POWER_SERVICE); + wakeLock = pm.newWakeLock(PowerManager.SCREEN_BRIGHT_WAKE_LOCK + | PowerManager.ACQUIRE_CAUSES_WAKEUP, + "OsmAndOnVoiceWakeupTag"); + wakeLock.acquire(); + } + if (keyguardLock == null) { + KeyguardManager km = (KeyguardManager) getSystemService(Context.KEYGUARD_SERVICE); + keyguardLock = km.newKeyguardLock("OsmAndKeyguardLock"); + keyguardLock.disableKeyguard(); + } + + uiHandler.postDelayed(new Runnable() { + + @Override + public void run() { + releaseWakeLocks(); + } + }, WAKE_ON_VOICE_INTERVAL); + } + } + + private void releaseWakeLocks() { + long now = System.currentTimeMillis(); + if (now >= lastWakeOnTime) { + if (keyguardLock != null) { + keyguardLock.reenableKeyguard(); + keyguardLock = null; + } + if (wakeLock != null) { + wakeLock.release(); + wakeLock = null; + } + } + } } diff --git a/OsmAnd/src/net/osmand/plus/routing/VoiceRouter.java b/OsmAnd/src/net/osmand/plus/routing/VoiceRouter.java index 6ea6648db7..168c1e5538 100644 --- a/OsmAnd/src/net/osmand/plus/routing/VoiceRouter.java +++ b/OsmAnd/src/net/osmand/plus/routing/VoiceRouter.java @@ -2,6 +2,7 @@ package net.osmand.plus.routing; import java.io.IOException; +import java.util.ArrayList; import java.util.List; import net.osmand.Location; @@ -23,6 +24,8 @@ import alice.tuprolog.Term; import android.content.Context; import android.media.AudioManager; import android.media.SoundPool; +import android.os.Handler; +import android.os.Looper; public class VoiceRouter { @@ -70,12 +73,24 @@ public class VoiceRouter { private long lastAnnouncement = 0; + public interface VoiceMessageListener { + void onVoiceMessage(); + } + private List voiceMessageListeners; + private Handler handler; + public VoiceRouter(RoutingHelper router, final OsmandSettings settings, CommandPlayer player) { this.router = router; this.player = player; this.settings = settings; empty = new Struct(""); + voiceMessageListeners = new ArrayList(); + Looper looper = Looper.myLooper(); + if (looper == null) { + looper = Looper.getMainLooper(); + } + handler = new Handler(looper); } public void setPlayer(CommandPlayer player) { @@ -211,6 +226,7 @@ public class VoiceRouter { if(waitAnnouncedOffRoute == 0 || ms - lastAnnouncedOffRoute > waitAnnouncedOffRoute) { CommandBuilder p = getNewCommandPlayerToPlay(); if (p != null) { + notifyOnVoiceMessage(); p.offRoute(dist).play(); } if(waitAnnouncedOffRoute == 0) { @@ -225,6 +241,7 @@ public class VoiceRouter { public void announceBackOnRoute() { CommandBuilder p = getNewCommandPlayerToPlay(); if (p != null) { + notifyOnVoiceMessage(); p.backOnRoute().play(); } } @@ -234,6 +251,7 @@ public class VoiceRouter { if (p == null){ return; } + notifyOnVoiceMessage(); double[] dist = new double[1]; makeSound(); String text = getText(location, points, dist); @@ -245,6 +263,7 @@ public class VoiceRouter { if (p == null){ return; } + notifyOnVoiceMessage(); double[] dist = new double[1]; makeSound(); String text = getText(location, points, dist); @@ -256,6 +275,8 @@ public class VoiceRouter { if (p == null){ return; } + + notifyOnVoiceMessage(); double[] dist = new double[1]; String text = getText(location, points, dist); p.goAhead(dist[0], null).andArriveAtPoiWaypoint(text).play(); @@ -266,6 +287,7 @@ public class VoiceRouter { if (p == null){ return; } + notifyOnVoiceMessage(); makeSound(); String text = getText(null, points,null); p.arrivedAtWayPoint(text).play(); @@ -276,6 +298,7 @@ public class VoiceRouter { if (p == null){ return; } + notifyOnVoiceMessage(); makeSound(); String text = getText(null, points,null); p.arrivedAtFavorite(text).play(); @@ -286,6 +309,7 @@ public class VoiceRouter { if (p == null){ return; } + notifyOnVoiceMessage(); String text = getText(null, points,null); p.arrivedAtPoi(text).play(); } @@ -315,6 +339,7 @@ public class VoiceRouter { if (router.getSettings().SPEAK_SPEED_CAMERA.get()) { CommandBuilder p = getNewCommandPlayerToPlay(); if (p != null) { + notifyOnVoiceMessage(); p.attention(type+"").play(); } } @@ -322,6 +347,7 @@ public class VoiceRouter { if (router.getSettings().SPEAK_TRAFFIC_WARNINGS.get()) { CommandBuilder p = getNewCommandPlayerToPlay(); if (p != null) { + notifyOnVoiceMessage(); p.attention(type+"").play(); } } @@ -342,6 +368,7 @@ public class VoiceRouter { } else if (router.getSettings().SPEAK_SPEED_LIMIT.get() && ms - waitAnnouncedSpeedLimit > 10 * 1000 ) { CommandBuilder p = getNewCommandPlayerToPlay(); if (p != null) { + notifyOnVoiceMessage(); lastAnnouncedSpeedLimit = ms; waitAnnouncedSpeedLimit = 0; p.speedAlarm().play(); @@ -503,6 +530,7 @@ public class VoiceRouter { private boolean playMakeUTwp() { CommandBuilder play = getNewCommandPlayerToPlay(); if(play != null){ + notifyOnVoiceMessage(); play.makeUTwp().play(); return true; } @@ -512,6 +540,7 @@ public class VoiceRouter { private void playGoAhead(int dist, Term streetName) { CommandBuilder play = getNewCommandPlayerToPlay(); if(play != null){ + notifyOnVoiceMessage(); play.goAhead(dist, streetName).play(); } } @@ -569,10 +598,13 @@ public class VoiceRouter { if(play != null){ String tParam = getTurnType(next.getTurnType()); if(tParam != null){ + notifyOnVoiceMessage(); play.prepareTurn(tParam, dist, getSpeakableStreetName(currentSegment, next)).play(); } else if(next.getTurnType().isRoundAbout()){ + notifyOnVoiceMessage(); play.prepareRoundAbout(dist, next.getTurnType().getExitOut(), getSpeakableStreetName(currentSegment, next)).play(); } else if(next.getTurnType().getValue() == TurnType.TU || next.getTurnType().getValue() == TurnType.TRU){ + notifyOnVoiceMessage(); play.prepareMakeUT(dist, getSpeakableStreetName(currentSegment, next)).play(); } } @@ -609,6 +641,7 @@ public class VoiceRouter { } } if(isPlay){ + notifyOnVoiceMessage(); play.play(); } } @@ -619,6 +652,7 @@ public class VoiceRouter { String pointName = info == null ? "" : info.pointName; CommandBuilder play = getNewCommandPlayerToPlay(); if (play != null) { + notifyOnVoiceMessage(); if (info != null && info.intermediatePoint) { play.andArriveAtIntermediatePoint(getSpeakablePointName(pointName)).play(); } else { @@ -661,6 +695,7 @@ public class VoiceRouter { isplay = true; } if(isplay){ + notifyOnVoiceMessage(); play.play(); } } @@ -690,6 +725,7 @@ public class VoiceRouter { public void gpsLocationLost(){ CommandBuilder play = getNewCommandPlayerToPlay(); if (play != null) { + notifyOnVoiceMessage(); play.gpsLocationLost().play(); } } @@ -697,6 +733,7 @@ public class VoiceRouter { public void gpsLocationRecover() { CommandBuilder play = getNewCommandPlayerToPlay(); if (play != null) { + notifyOnVoiceMessage(); play.gpsLocationRecover().play(); } @@ -710,11 +747,13 @@ public class VoiceRouter { // suppress "route recalculated" prompt for 60sec (this workaround now outdated after more intelligent route recalculation and directional voice prompt suppression) // if (router.getCurrentGPXRoute() == null && (System.currentTimeMillis() - lastTimeRouteRecalcAnnounced > 60000)) { if (router.getCurrentGPXRoute() == null) { + notifyOnVoiceMessage(); play.routeRecalculated(router.getLeftDistance(), router.getLeftTime()).play(); currentStatus = STATUS_UNKNOWN; // lastTimeRouteRecalcAnnounced = System.currentTimeMillis(); } } else { + notifyOnVoiceMessage(); play.newRouteCalculated(router.getLeftDistance(), router.getLeftTime()).play(); currentStatus = STATUS_UNKNOWN; } @@ -729,6 +768,7 @@ public class VoiceRouter { public void arrivedDestinationPoint(String name) { CommandBuilder play = getNewCommandPlayerToPlay(); if(play != null){ + notifyOnVoiceMessage(); play.arrivedAtDestination(getSpeakablePointName(name)).play(); } } @@ -736,6 +776,7 @@ public class VoiceRouter { public void arrivedIntermediatePoint(String name) { CommandBuilder play = getNewCommandPlayerToPlay(); if(play != null){ + notifyOnVoiceMessage(); play.arrivedAtIntermediatePoint(getSpeakablePointName(name)).play(); } } @@ -744,6 +785,7 @@ public class VoiceRouter { //public void arrivedWayPoint(String name) { // CommandBuilder play = getNewCommandPlayerToPlay(); // if(play != null){ + // notifyOnVoiceMessage(); // play.arrivedAtWayPoint(getSpeakablePointName(name)).play(); // } //} @@ -779,8 +821,10 @@ public class VoiceRouter { int time = voiceRouter.router.getLeftTime(); if (left > 0) { if (type == ROUTE_CALCULATED) { + notifyOnVoiceMessage(); newCommand.newRouteCalculated(left, time).play(); } else if (type == ROUTE_RECALCULATED) { + notifyOnVoiceMessage(); newCommand.routeRecalculated(left, time).play(); } } @@ -802,5 +846,43 @@ public class VoiceRouter { } } + public void addVoiceMessageListener(VoiceMessageListener voiceMessageListener) { + synchronized (voiceMessageListeners) { + if (!voiceMessageListeners.contains(voiceMessageListener)) { + voiceMessageListeners.add(voiceMessageListener); + } + } + } + + public void removeVoiceMessageListener(VoiceMessageListener voiceMessageListener) { + synchronized (voiceMessageListeners) { + if (voiceMessageListeners.contains(voiceMessageListener)) { + voiceMessageListeners.remove(voiceMessageListener); + } + } + } + public void notifyOnVoiceMessage() { + handler.post(new Runnable() { + + @Override + public void run() { + synchronized (voiceMessageListeners) { + for (final VoiceMessageListener voiceMessageListener : voiceMessageListeners) { + Runnable closure = new Runnable() { + public void run() { + synchronized (voiceMessageListeners) { + if (voiceMessageListeners + .contains(voiceMessageListener)) { + voiceMessageListener.onVoiceMessage(); + } + } + } + }; + handler.post(closure); + } + } + } + }); + } } From 517b0a68e4d45f6d6e6127f566cd0edc3b0586bb Mon Sep 17 00:00:00 2001 From: Taranenko Roman Date: Thu, 30 Oct 2014 22:55:26 +0200 Subject: [PATCH 2/2] Improving the Route Details view --- .../res/layout-large/route_info_list_item.xml | 38 +++++++++---------- OsmAnd/res/layout/route_info_list_item.xml | 34 ++++++++--------- 2 files changed, 36 insertions(+), 36 deletions(-) diff --git a/OsmAnd/res/layout-large/route_info_list_item.xml b/OsmAnd/res/layout-large/route_info_list_item.xml index 0d32ed0465..4a9748f4ff 100644 --- a/OsmAnd/res/layout-large/route_info_list_item.xml +++ b/OsmAnd/res/layout-large/route_info_list_item.xml @@ -3,6 +3,25 @@ android:layout_width="fill_parent" android:layout_height="wrap_content" > + + + + + + + - - - - - - - \ No newline at end of file diff --git a/OsmAnd/res/layout/route_info_list_item.xml b/OsmAnd/res/layout/route_info_list_item.xml index e503c54147..70a7c17aa9 100644 --- a/OsmAnd/res/layout/route_info_list_item.xml +++ b/OsmAnd/res/layout/route_info_list_item.xml @@ -3,6 +3,23 @@ android:layout_width="fill_parent" android:layout_height="wrap_content" > + + + + + + + - - - - - - - \ No newline at end of file