Skip to content

Commit

Permalink
Merge pull request #20902 from osmandapp/lock_screen
Browse files Browse the repository at this point in the history
Add lock screen quick action
  • Loading branch information
Chumva authored Oct 1, 2024
2 parents 42e1083 + 5693b77 commit 62d7f72
Show file tree
Hide file tree
Showing 9 changed files with 217 additions and 1 deletion.
2 changes: 2 additions & 0 deletions OsmAnd/res/values/strings.xml
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@
- For wording and consistency, please note https://docs.osmand.net/docs/technical/contributions/translating-osmand
Thx - Hardy
-->
<string name="lock_screen_description">Enables or disables touch screen functionality to prevent accidental taps</string>
<string name="lock_screen">Lock screen</string>
<string name="track_does_not_contain_data_to_save">Track doesn\'t contain data to save.</string>
<string name="quick_action_finish_trip_recording_summary">A button to save the GPX track and finish trip recording.</string>
<string name="start_trip_recording_first_m">Please start trip recording first.</string>
Expand Down
4 changes: 4 additions & 0 deletions OsmAnd/src/net/osmand/plus/activities/MapActivity.java
Original file line number Diff line number Diff line change
Expand Up @@ -1365,6 +1365,10 @@ public boolean isDrawerAvailable() {

@Override
public boolean dispatchTouchEvent(MotionEvent event) {
if (lockHelper.isScreenLocked()) {
return lockHelper.getLockGestureDetector(this).onTouchEvent(event);
}

if (settings.DO_NOT_USE_ANIMATIONS.get()) {
if (event.getAction() == MotionEvent.ACTION_DOWN) {
if (drawerLayout.isDrawerOpen(GravityCompat.START)) {
Expand Down
1 change: 1 addition & 0 deletions OsmAnd/src/net/osmand/plus/helpers/AndroidUiHelper.java
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
import android.content.pm.PackageManager;
import android.content.res.Configuration;
import android.graphics.Color;
import android.graphics.Rect;
import android.os.Build;
import android.os.Build.VERSION_CODES;
import android.util.DisplayMetrics;
Expand Down
84 changes: 84 additions & 0 deletions OsmAnd/src/net/osmand/plus/helpers/LockGestureDetector.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
package net.osmand.plus.helpers;

import android.util.Pair;
import android.view.GestureDetector;
import android.view.MotionEvent;

import androidx.annotation.NonNull;

import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.quickaction.QuickAction;
import net.osmand.plus.quickaction.actions.LockScreenAction;
import net.osmand.plus.utils.AndroidUtils;
import net.osmand.plus.views.controls.maphudbuttons.QuickActionButton;
import net.osmand.plus.views.layers.MapQuickActionLayer;
import net.osmand.plus.views.mapwidgets.configure.buttons.QuickActionButtonState;

public class LockGestureDetector extends GestureDetector {
private final MapActivity mapActivity;
private Pair<QuickAction, QuickActionButton> pressedLockAction;

public LockGestureDetector(@NonNull MapActivity mapActivity, @NonNull OnGestureListener listener) {
super(mapActivity, listener);
this.mapActivity = mapActivity;
}

@Override
public boolean onTouchEvent(MotionEvent ev) {
if (ev.getAction() == MotionEvent.ACTION_DOWN) {
pressedLockAction = getPressedLockAction(mapActivity, ev);
if (pressedLockAction != null) {
pressedLockAction.second.setPressed(true);
}
} else if (ev.getAction() == MotionEvent.ACTION_UP) {
if (pressedLockAction != null) {
pressedLockAction.second.setPressed(false);
}
}
return super.onTouchEvent(ev);
}

private static Pair<QuickAction, QuickActionButton> getPressedLockAction(@NonNull MapActivity mapActivity, @NonNull MotionEvent ev) {
float x = ev.getRawX();
float y = ev.getRawY();
QuickActionButton quickActionButton;
QuickAction lockAction;
MapQuickActionLayer quickActionLayer = mapActivity.getMapLayers().getMapQuickActionLayer();
for (QuickActionButton actionButton : quickActionLayer.getActionButtons()) {
QuickActionButtonState buttonState = actionButton.getButtonState();
if (buttonState != null) {
for (QuickAction action : buttonState.getQuickActions()) {
if (action instanceof LockScreenAction && AndroidUtils.getViewBoundOnScreen(actionButton).contains((int) x, (int) y)) {
quickActionButton = actionButton;
lockAction = action;
return new Pair<>(lockAction, quickActionButton);
}
}
}
}
return null;
}

private static OnGestureListener getOnGestureListener(@NonNull MapActivity mapActivity) {
return new GestureDetector.SimpleOnGestureListener() {
@Override
public boolean onSingleTapConfirmed(@NonNull MotionEvent e) {
Pair<QuickAction, QuickActionButton> pressedLockAction = getPressedLockAction(mapActivity, e);

if (pressedLockAction != null) {
QuickAction lockAction = pressedLockAction.first;
QuickActionButtonState buttonState = pressedLockAction.second.getButtonState();
if (buttonState != null) {
mapActivity.getMapLayers().getMapQuickActionLayer().onActionSelected(buttonState, lockAction);
return true;
}
}
return false;
}
};
}

public static LockGestureDetector getDetector(@NonNull MapActivity mapActivity) {
return new LockGestureDetector(mapActivity, getOnGestureListener(mapActivity));
}
}
65 changes: 64 additions & 1 deletion OsmAnd/src/net/osmand/plus/helpers/LockHelper.java
Original file line number Diff line number Diff line change
Expand Up @@ -11,27 +11,36 @@
import android.os.PowerManager;
import android.os.PowerManager.WakeLock;
import android.provider.Settings;
import android.view.GestureDetector;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;

import net.osmand.PlatformUtil;
import net.osmand.StateChangedListener;
import net.osmand.plus.OsmandApplication;
import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.quickaction.QuickAction;
import net.osmand.plus.quickaction.actions.LockScreenAction;
import net.osmand.plus.settings.backend.ApplicationMode;
import net.osmand.plus.settings.backend.OsmAndAppCustomization.OsmAndAppCustomizationListener;
import net.osmand.plus.settings.backend.OsmandSettings;
import net.osmand.plus.settings.backend.preferences.CommonPreference;
import net.osmand.plus.routing.VoiceRouter.VoiceMessageListener;
import net.osmand.plus.views.mapwidgets.configure.buttons.QuickActionButtonState;

import org.apache.commons.logging.Log;

import java.util.List;

public class LockHelper implements SensorEventListener {
public class LockHelper implements SensorEventListener, StateChangedListener<ApplicationMode> {

private static final Log LOG = PlatformUtil.getLog(LockHelper.class);

private static final int SENSOR_SENSITIVITY = 4;

private static boolean lockScreen = false;

@Nullable
private WakeLock wakeLock;

Expand All @@ -43,10 +52,12 @@ public class LockHelper implements SensorEventListener {
private CommonPreference<Boolean> turnScreenOnPowerButton;
private CommonPreference<Boolean> turnScreenOnNavigationInstructions;

private ApplicationMode lastApplicationMode;
@Nullable
private LockUIAdapter lockUIAdapter;
private final Runnable lockRunnable;
private final VoiceMessageListener voiceMessageListener;
private LockGestureDetector gestureDetector;

public interface LockUIAdapter {

Expand All @@ -65,6 +76,7 @@ public LockHelper(OsmandApplication app) {
turnScreenOnPowerButton = settings.TURN_SCREEN_ON_POWER_BUTTON;
turnScreenOnNavigationInstructions = settings.TURN_SCREEN_ON_NAVIGATION_INSTRUCTIONS;

settings.APPLICATION_MODE.addListener(this);
lockRunnable = this::lock;
voiceMessageListener = new VoiceMessageListener() {
@Override
Expand Down Expand Up @@ -201,4 +213,55 @@ public void onStop(@NonNull Activity activity) {
public void setLockUIAdapter(@Nullable LockUIAdapter adapter) {
lockUIAdapter = adapter;
}

/**
* LockScreenAction part
*/


public void toggleLockScreen() {
lockScreen = !lockScreen;
}

public boolean isScreenLocked() {
return lockScreen;
}

public void unlockScreen() {
lockScreen = false;
}

@Override
public void stateChanged(ApplicationMode mode) {
List<QuickActionButtonState> buttonStates = app.getMapButtonsHelper().getButtonsStates();
ApplicationMode currentMode = app.getSettings().getApplicationMode();

if (isScreenLocked() && lastApplicationMode != currentMode) {
if (!hasLockScreenAction(buttonStates)) {
unlockScreen();
}
}
lastApplicationMode = currentMode;
}

private boolean hasLockScreenAction(@NonNull List<QuickActionButtonState> mapButtonStates) {
for (QuickActionButtonState buttonState : mapButtonStates) {
if (!buttonState.isEnabled()) {
continue;
}
for (QuickAction action : buttonState.getQuickActions()) {
if (action instanceof LockScreenAction) {
return true;
}
}
}
return false;
}

public GestureDetector getLockGestureDetector(@NonNull MapActivity mapActivity) {
if (gestureDetector == null) {
gestureDetector = LockGestureDetector.getDetector(mapActivity);
}
return gestureDetector;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -391,6 +391,7 @@ public void updateActionTypes() {
allTypes.add(OpenSearchViewAction.TYPE);
allTypes.add(ShowHideDrawerAction.TYPE);
allTypes.add(NavigatePreviousScreenAction.TYPE);
allTypes.add(LockScreenAction.TYPE);

List<QuickActionType> enabledTypes = new ArrayList<>(allTypes);
PluginsHelper.registerQuickActionTypesPlugins(allTypes, enabledTypes);
Expand Down
1 change: 1 addition & 0 deletions OsmAnd/src/net/osmand/plus/quickaction/QuickActionIds.java
Original file line number Diff line number Diff line change
Expand Up @@ -74,4 +74,5 @@ public class QuickActionIds {
public static final int START_NEW_TRIP_SEGMENT_ACTION = 74;
public static final int SAVE_RECORDED_TRIP_AND_CONTINUE_ACTION = 75;
public static final int FINISH_TRIP_RECORDING_ACTION = 76;
public static final int LOCK_SCREEN_ACTION = 77;
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
package net.osmand.plus.quickaction.actions;

import static net.osmand.plus.quickaction.QuickActionIds.LOCK_SCREEN_ACTION;

import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;

import androidx.annotation.NonNull;

import net.osmand.plus.OsmandApplication;
import net.osmand.plus.R;
import net.osmand.plus.activities.MapActivity;
import net.osmand.plus.quickaction.QuickAction;
import net.osmand.plus.quickaction.QuickActionType;

public class LockScreenAction extends QuickAction {

public static final QuickActionType TYPE = new QuickActionType(LOCK_SCREEN_ACTION,
"lock_screen_action", LockScreenAction.class)
.nameRes(R.string.lock_screen)
.iconRes(R.drawable.ic_action_touch_screen_lock)
.category(QuickActionType.INTERFACE)
.nameActionRes(R.string.quick_action_verb_turn_on_off);

public LockScreenAction() {
super(TYPE);
}

public LockScreenAction(QuickAction quickAction) {
super(quickAction);
}

@Override
public void execute(@NonNull MapActivity mapActivity) {
mapActivity.getMyApplication().getLockHelper().toggleLockScreen();
mapActivity.getMapLayers().getMapQuickActionLayer().refreshLayer();
}

@Override
public void drawUI(@NonNull ViewGroup parent, @NonNull MapActivity mapActivity) {
View view = LayoutInflater.from(parent.getContext())
.inflate(R.layout.quick_action_with_text, parent, false);
((TextView) view.findViewById(R.id.text)).setText(mapActivity.getString(R.string.lock_screen_description));
parent.addView(view);
}

@Override
public int getIconRes(Context context) {
OsmandApplication app = (OsmandApplication) context.getApplicationContext();
return app.getLockHelper().isScreenLocked() ? R.drawable.ic_action_touch_screen_unlock : R.drawable.ic_action_touch_screen_lock;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -139,6 +139,11 @@ private void updateButtons() {
}
}

@NonNull
public List<QuickActionButton> getActionButtons() {
return actionButtons;
}

public void refreshLayer() {
setSelectedButton(null);
isLayerOn = mapButtonsHelper.hasEnabledButtons();
Expand Down

0 comments on commit 62d7f72

Please sign in to comment.