I have a bunch of activities tied together, one into the next and so on. Now during one activity I want to measure elapsed time. As I understand, I would use System.nanoTime() to find the start time, the user does some things, then use it once more to find the end time, subtract the two and voila my elapsed time spent on the activity. But suppose something happens while my activity is running: I already have created the start time, but now the user gets a phone call or something, my activity is put into the background. The phone call ends and the user returns to the activity. Was the timer running the whole time, even while the app was in the background? Is the timer 'reset' since I left the app then came back to it?
Also, when I do initiate System.nanoTime() is it returning the time since the start of that particular activity or the main activity?
EDIT: Suppose I set the first tickmark at a certain point, then the app goes into the background, then it returns to the foreground and I set the second tickmark. Ideally I want the time elapsed along with the time spent in the background; does System.nanoTime() achieve this?
static long nanoTime():
Returns the current timestamp of the most precise timer available on the local system.
You aren't using a "Timer" (that is, a stateful object of any kind) to represent the elapsed time, you are just hanging on to a long. As you pointed out, you will call System.nanoTime() again at some future point and subtract to find the elapsed time.
If you want to exclude time spent outside of this activity, like the example in your question, you will need to use onPause() and onResume() to help you manage the calculations. Or, if you switch to some kind of timer object, use these methods to pause and resume the timer.
You can "start" your "timer" wherever you think makes the most sense. If it's when the user initiates some action (like a button press), od it in an OnClickListener. If it's just to measure how long some method/code path runs, do it at the beginning of that.
according to the doc
System.nanoTime() returns the current value of the most precise
available system timer, in nanoseconds.
So it is not an timer. It just returns the system time in nano seconds. It has not relation with activity.
If you want to measure the lifetime of activity then get the time in onCreate and onDestroy. And if you want the time to know how much time the activity was in foreground then get the time in onResume and onPause.
You will need to override onPause() and onResume() methods in the Activity class so you can pause your timer in pause. and resume in onResume.
You should put System.nanoTime() on onResume()
Related
How to create a timer runed in the background and display one second of a second in the TextView dynamically in MainActivity.Whatever I exit app or leaving the MainActivity,the timer also keep on.
I thinked that I can use service and BroadcastReceiver or using Handler and Thread.But I can't solve it.
Having an always-on service to simply count up seconds is a bad idea, it'll waste battery life and could be killed at any time.
What you could do is something like this:
Make a counter that you can start/stop with a button.
On your your activity's onPause, save the System.currentTimeInMillis() along with the current count on your timer
When you resume your activity, use the current System.currentTimeInMillis() value to calculate what your timer should be displaying had it been really running all that time.
I have thinked a solution; Thread+Handler; EveryTime enter ther MainActivity
we just set the time interval = EndTime-System.currentTimeMillis();
I am trying to write to a file whenever the user has not interacted with the application for 2 minutes. Currently am having base activity in which I have overriden the onUserInteraction method. In this method the float time variable is reset and onResume I subtract the time with the current time to check if two minutes have passed. This works fine but sometimes acts crazy. Second approach was using the postDelayed method of the Handler and start a thread. This works perfectly but does not include the case when the app goes to background or the device goes to sleep.Is there a way to cover all these cases. ahve researched a lot. Also came across Wakeful Intent service but read that it is expensive.
Is there a way to cover all these cases.
Yes. ... and it is expensive. Waking the phone up, every 2 minutes is going to drain the battery like crazy.
That said, the answer to your question is that you need to use the AlarmManager, probably in concert with either the WakefulIntentService or the WakefulBroadcastReceiver. Create a PendingIntent and schedule it for delivery every 2 minutes.
I don't know a way of tracking inactivity but there is a way to track user activity. You can catch a callback called onUserInteraction() in your activities that is called every time the user does any interaction with the application. I'd suggest doing something like this:
#Override
public void onUserInteraction(){
MyTimerClass.getInstance().resetTimer();
}
If your app contains several activities, why not put this method in an abstract super class (extending Activity) and then have all you activities extending it.
I need to calculate the time taken by my app to start. Do you have any ideas when to start and when to stop timing?
Use your timer at the beginning of oncreate() and stop it at the end of onResume().
According to lifecycle of an Activity.
To do this, you probably should be clear on what "start my app" means - if you are referring to an activity, then you should probably override the Activity constructor (not "onCreate" except in most cases there isn't any measurable time from the constructor before onCreate is called) and capture:
SystemClock.upTimeMillis()
then you need to create a listener for onGlobalLayout to determine when the activity is actually finished displaying on the screen and get the upTime again. For the listener, do it like in this post:
Activity lifecycle - receiving notification that layout is complete
And then take the difference between the times... however, that is really the "activity" startup time.
If you are certain your app is not running, and you want to see how long it takes to "start your app" when it is not loaded in memory at all, you should extend the Application class:
public class MyApp extends Application {
public MyApp() {
// get the time
}
}
and then override the constructor to capture the timestamp like above and store it. Your app's application class is constructed first, then activities are instantiated.
Then capture the listener time in the first activity to display, as mentioned above. That will probably tell you best how much time it took from when your app "starts" to when the user actually could see it.
There are a few things that happen between when a user action occurs that is intended to "start your app" that are not included, but you have no control over that, even though that should be included if you are trying to measure how long it takes from the user's perspective.
How would I calculate the total time an activity has been displayed on the screen? It should be the total time it had been on screen, across its various launches, since it has been installed.
Keep a static time variable. Start a new timer every time your activity is on screen, that is when onResume is called. And suspend the timer when your activity goes out of screen, that is onPause, onStop, onDestroy and add the time elapsed to the time variable.
Copa's answer will be very useful to count the time through many sessions of your application.
Use the activity lifecircle callback functions to detect what happend to your activity:
http://developer.android.com/reference/android/app/Activity.html
The information how long an activity lived can be stored using the SharedPreferences:
http://developer.android.com/reference/android/content/SharedPreferences.html
I am calculating creating apps for Online Shopping in which i am having a Deals Start Date and End Date..
From this two date i want to calculate the time remaining for the Deal to end in Seconds basis.. I calculated remaining days,seconds,hours,minutes..
I want to display the Remaining time in Days:Hours:Minutes:Seconds format...
Although i move to next activity this time should runs in background in which the second must updated every seconds..
If i move this activity again i want to display the Updated Remaining time...
Also in my UI the Remaining time must get reduced second by second.
Instead of building a service I would create a Handler that updates your Userinterface.
You can now call sendEmptyMessageDelayed with a delay of 1000ms. In the handleMessage method you can update your UI and call sendEmptyMessageDelayed again.
Don't count on Android to call you exactly in time. recalculate the remaining time every now and then instead of just decreasing it by one.
If the activity is in the background you shouldn't update the UI because the activity is paused. Just disable the whole updating process in the onPause method and reenable it in your onResume method. If you method is destroyed from the system while it was in the background your onCreate method will be called again and you have to recalculate the actual remaining time.
Make sure you understand the ActivityLifecycle Process before implementing this changes.
Sounds like you need a Service and an Activity with the Service performing the timing operation and the Activity presenting the time information.