Is it possible to detect motion when screen is off? - android

My app simply need to detect any motion of the device while screen is off.
I know that accelerometer is used for this task but it don't work while screen is off in all devices. this is a list of devices http://www.saltwebsites.com/2012/android-accelerometers-screen-off
so is there a way of taking accelerometer sensor data while screen is off that works on all devices?
or is there a way to detect motion using another sensors?

Partial Wake Lock is all you need to access accelerometer readings while the screen is off.
You can use it like this:
private PowerManager.WakeLock mWakeLock;
PowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE);
mWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "My Tag");
mWakeLock.acquire();
And after you're done, just release the lock:
mWakeLock.release();
If you obtain accelerometer data in a Service, you could simply acquire lock in it's onCreate() and release in onDestroy().

Yes you can use accelerometer in the background or when screen is off
but you need to hold a WakeLock [Link] to prevent the device from sleeping.
If you need to detect if the device is still or if it started moving again you might be interested in Recognizing the User's Current Activity from Google Services.

After a quick research I found that most of android devices does not send the accelarometer events when the screen is off. To know more about this bug please take a look on here. Also here too.

When the screen is off the CPU goes to sleep and you cannot capture events without taking a partial wakelock. I suggest you to take a partial wakelock when you call the onPause and release it onResume. Be careful with wakelocks they make your phone drain a really big amount of energy, you should manage them carefully.
PS: You have to acquire the wakelock in the onPause method because if you try to call it somewhere else you might not be able to gain it because the CPU may be already shutted down.

Related

PowerManager and PARTIAL_WAKE_LOCK

My app works fine when the device is plugged in the power supply whereas it fails (time to time) when the device is unplugged. I think that the piece of code responsible of this issue is as follows:
PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wl = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "foo");
wl.acquire();
foo();
wl.release();
foo() is a function that invokes a Camera.takePicture() that, as you know, results in a parallel task that takes a couple of seconds to complete. Thus, wl.release() is actually called when the picture has not yet taken. The above code is executed by an alarm which wakeup the device from its standby mode. My question is, is there the risk that the device returns in its standby mode before the picture has been taken due to the fact that wl.release might be called before the picture is taken? Does wl.release() release instantaneously the PARTIAL_WAKE_LOCK or the device remains in its run mode for a while?
Many thanks in advance for any comment.
My question is, is there the risk that the device returns in its standby mode before the picture has been taken due to the fact that wl.release might be called before the picture is taken?
Yes.
Does wl.release() release instantaneously the PARTIAL_WAKE_LOCK
Yes.
or the device remains in its run mode for a while?
That depends on what else might be holding a WakeLock.

PowerManager newWakeLock.acquire() not working as expected

I want my app to keep the CPU running but turn the screen off to minimise power wastage.
Previous posts on this subject suggest the following approach:
mPm = (PowerManager) getSystemService(Context.POWER_SERVICE);
mWakeLock = mPm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, Constants.WAKE_LOCK_TAG);
mWakeLock.acquire(); //keep CPU running, turn screen off
The manifest contains:
<uses-permission android:name="android.permission.WAKE_LOCK" />
In my innocence I expected that on acquiring the lock the screen would go off immediately but nothing happened.
The earlier posts I have read never seem to overcome this problem, did anyone succeed? Is there anything else I must do?
It would be more efficient in another way to use this within the onCreate method of the activity:
getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);
That is a better way to use wake-locks in a efficient manner.
The wake lock does not turn off the screen. Normally, when the screen goes off, your application pauses because the CPU is put to sleep. If you have PARTIAL_WAKE_LOCK, your app will continue to run and the CPU will be active even when the screen goes off (due to auto or manual sleeping). Only use this if you really need to continue processing data after the screen is off. You mention you are concerned about minimizing power usage, acquiring a wake lock of any kind can cause waster power. It is wise to follow this warning from the PowerManager docs
Device battery life will be significantly affected by the use of this
API. Do not acquire PowerManager.WakeLocks unless you really need
them, use the minimum levels possible, and be sure to release them as
soon as possible.
So it is good idea to evaluate why you think you need a wake lock for your task. If you think it is too save power, it isn't.

Android Native timer for bringing back the device to wake up mode?

I want to launch a timer which will get fired when the timer gets expired when the device is in low power (sleep) mode.
Device only gets waked up (normal mode) either on hard ware event (pressing of power button) or any network activity (call or data packet receiving).
Is there any way to bring the device back to the normal mode with timers in the native layer of android?
I googled so much but not able to find a way. Tried using timer_create() as well. But its not getting fired when the device is in low power (sleep) mode.
Please let me know if anyone had already done on this part.
Actually precision required for me is in milliseconds and the AlarmManager with RTC_WAKEUP is in the application layer which is expiring after consider delay and also this is in the Java layer. (If I implement Jni it will make some overhead to the application as there are multiple timers which need to be run in sleep mode).
To bring back the device up i think you can explore on these lines
1. PowerMangerService
PowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE);
PowerManager.WakeLock wl = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK, "My Tag");
wl.acquire();
//..screen will stay on during this section..
wl.release();
2. android.provider.Settings.System.SCREEN_OFF_TIMEOUT value in the settings for screen time out.
3. Intent.ACTION_SCREEN_ON and Intent.ACTION_SCREEN_OFF intents by PowerManagerService

PARTIAL_WAKE_LOCK when recording sensor data

I am recording sensor data such as Accelerometer, Orientation, Gyroscope. This data writes to a file onSensorChanged update every so often.
My problem is when I put the phone into standby that the sensor data stops writing to file. So I done some research and decided to set it up using PowerManager and using the wake lock
PARTIAL_WAKE_LOCK: I just can't get it working.
SCREEN_DIM_WAKE_LOCK: My code will work grand.
From what I read up on there seems to be a problem with using PARTIAL_WAKE_LOCK.
I can't seem to find a definite answer on whether or not there is a problem with it still or there isn't. I even tried some of the hack approaches people have suggested such as using an itent to capture when screen is off and then unregistering the sensors and registering them again. But this solution didn't work. From what I can gather it seems inconsistant if it will work or not and seems phone dependant. I have tried my code on both a HTC Wildfire running Android2.2 and Nexus S running Android2.3.
My application is an app that is basically ran in the background with a long running service. So having PARTIAL_WAKE_LOCK is important with battery life.
This is only defined to work as of Android 2.3. Prior to that the platform would explicitly turn off all sensors when the screen turns off in order to reduce battery use.
This is a pretty old question, I'll still answer it as pretty much all the devices today are beyond 2.3
Create a background service and use the Partial Lock Wake in the following manner:
First take care of the permissions (in the manifest file):
<uses-permission android:name="android.permission.WAKE_LOCK" />
Then, most preferably use this in the Application file, or wherever:
PowerManager powerManager = (PowerManager) getSystemService(POWER_SERVICE);
PowerManager.WakeLock wakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK,
"MyWakelockTag");
if(/*condition*/) {
wakeLock.acquire(); //keep CPU awake
} else {
wakeLock.release(); //disable keep CPU awake
}
Although it is a pretty cool feature, it drains your battery life, hence use it responsibly.

How can I keep my Android service running when the screen is turned off?

When the screen turns off, my application service is paused.
I start my service with the following code:
if (mSharedPrefs.getBoolean("prefAutoUpdatesMain", false)) {
Intent svc = new Intent(this, MyService.class);
startService(svc);
}
How can I can avoid the service pause?
What I have to do in MyService is to download some data from Internet. If I have understand the process I have to follow is:
Acquire wakeLock
Download data
Release wakeLock
In downloading data method there are no reference to wakeLock, it is the application to have the wakeLock, is it correct?
Wake locks are reference counted by default. I think it is better a wakeLock without reference counting, to be sure to release it, am I wrong?
A partial WakeLock is what you want. It will hold the CPU open, even if the screen is off.
To acquire:
PowerManager mgr = (PowerManager)context.getSystemService(Context.POWER_SERVICE);
WakeLock wakeLock = mgr.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "MyWakeLock");
wakeLock.acquire();
To release:
wakeLock.release();
WakeLock also supports reference counting so you may have multiple things in your service that require wake functionality, and the device can sleep when none of them are active.
Things to watch out for:
If you use reference counting, make sure all control paths through your application will properly acquire/release...finally blocks come in handy here.
Also be sure to hold WakeLocks infrequently and for short periods of time. They add up in terms of battery use. Acquire your lock, do your business, and release as soon as possible.
You need a partial wake lock.
Detailed example here in a previous question:
Wake locks android service recurring
I'm just using a foregrgound service.

Categories

Resources