Android: Pause/Resume Timer OR Thread - java

I have checked all SO answers about how to pause/resume timer, but can't find a solution.
I have created a Timer task which counts the effort time for an employee and puts it inside a TextView to show.
Code below:
Timer T = new Timer();
T.scheduleAtFixedRate(new TimerTask() {
#Override
public void run() {
runOnUiThread(new Runnable() {
#Override
public void run() {
String workingTime = "Your effort is "
+ format.format(Double.valueOf(hr)) + ":"
+ format.format(Double.valueOf(min)) + ":"
+ format.format(Double.valueOf(sec))
+ " till now for the day";
storeEffort.setText(workingTime);
sec++;
if (sec > 59) {
sec = 0;
min = min + 1;
}
if (min > 59) {
min = 0;
hr = hr + 1;
}
}
});
}
}, 1000, 1000);
where storeEffort is my TextView which shows the effort time which is stuck inside the running thread(main problem). I want to pause the effort timer with a button click and resume it when the same button clicked again.Is there any other way to do this kind of task?

You solution might have a slight problem - you are using timer to count time intervals whereas there is no need to. You could use i.e. StopWatch to count elapsed time. So instead of adding seconds in a timer job you could just get elapsed time from this timer. To pause the timer you could call stopWatch.stop() and to start it, you could call stopWatch.start().
It could look like this:
Stopwatch stopwatch = Stopwatch.createStarted();
void startThreadUpdateTimer(){}
Timer T = new Timer();
T.scheduleAtFixedRate(new TimerTask() {
#Override
public void run() {
runOnUiThread(new Runnable() {
#Override
public void run() {
String workingTime = "Your effort is " + sw.toString() +
" till now for the day";
}
});
}
}, 1000, 1000);
}
public void pause(){
if(stopwatch.isRunning()){
stopwatch.stop();
}
}
public void resume(){
if(!stopwatch.isRunning()){
stopwatch.start();
}
}

UPDATE Solution if the timer needs to start from beginning every second time:
public class YourOuterClass extends Activity {
private YourTimerTask mTimerTask;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Button button;
button.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
if (mTimerTask != null && mTimerTask.isTaskActive()) {
mTimerTask.deactivateTimer();
mTimerTask = null;
} else {
startTask();
}
}
});
...
}
private class YourTimerTask extends TimerTask {
private boolean mIsTimerActive;
public YourTimer() {
mIsTimerActive = true;
}
public void deactivateTimer() {
mIsTimerActive = false;
}
public boolean isTaskActive() {
return mIsTimerActive;
}
#Override
public void run() {
runOnUiThread(new Runnable() {
#Override
public void run() {
String workingTime = "Your effort is "
+ format.format(Double.valueOf(hr)) + ":"
+ format.format(Double.valueOf(min)) + ":"
+ format.format(Double.valueOf(sec))
+ " till now for the day";
if (!mIsTimerActive) {
cancel(); // will cancel this timer instance
}
sec++;
if (sec > 59) {
sec = 0;
min = min + 1;
}
if (min > 59) {
min = 0;
hr = hr + 1;
}
}
});
}
}
...
private void startTask() {
Timer T = new Timer();
mTimerTask = new YourTimertask();
T.scheduleAtFixedRate(mTimerTask, 1000, 1000);
}
}

Related

Countdown Timer not counting correctly

When I pause the timer and then start it again it seems like the timer counts the current second again. For example it is 00:10, after half a second I stop the timer and when I start it again instead of going from 00:10 to 00:09 in half a second it counts a full second. I can't find what is wrong. Thanks for any help.
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_timer_2);
//...
Timer buttonTimer = new Timer();
buttonTimer.schedule(new TimerTask() {
#Override
public void run() {
runOnUiThread(new Runnable() {
if (timer_2_up_running) {
pausetimer_2_up();
starttimer_2_down();
} else {
starttimer_2_up();
if (timer_2_down_running) {
pausetimer_2_down();
private void starttimer_2_up() {
timer_2_up_countdowntimer = new CountDownTimer(starttimeup, 1000) {
#Override
public void onTick(long millisUntilFinished) {
starttimeup = millisUntilFinished;
update_up_text();
#Override
public void onFinish() {
timer_2_up_running = false;
}
}.start();
timer_2_up_running = true;
}
private void starttimer_2_down() {
timer_2_down_countdowntimer = new CountDownTimer(starttimedown, 1000) {
#Override
public void onTick(long millisUntilFinished) {
starttimedown = millisUntilFinished;
update_down_text();
}
#Override
public void onFinish() {
timer_2_down_running = false;
}
}.start();
timer_2_down_running = true;
}
private void pausetimer_2_up() {
timer_2_up_countdowntimer.cancel();
timer_2_up_running = false;
}
private void pausetimer_2_down() {
timer_2_down_countdowntimer.cancel();
timer_2_down_running = false;
}
private void update_up_text() {
int minutes_up = (int) (starttimeup / 1000) / 60;
int seconds_up = (int) (starttimeup / 1000) % 60;
String time_2_up_left_formatted = String.format(Locale.getDefault(), "%02d:%02d", minutes_up, seconds_up);
timer_2_up.setText(time_2_up_left_formatted);
}
private void update_down_text() {
int minutes_down = (int) (starttimedown / 1000) / 60;
int seconds_down = (int) (starttimedown / 1000) % 60;
String time_2_down_left_formatted = String.format(Locale.getDefault(), "%02d:%02d", minutes_down, seconds_down);
timer_2_down.setText(time_2_down_left_formatted);
}
You can use Chronometer to display recording time. start the
Chronometer when recording start and stop it when recording stop
<Chronometer
android:id="#+id/chronometerRecordTime"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_above="#+id/relativeLayout_bottom_video_controls"
android:layout_centerInParent="true"
android:layout_marginBottom="20dp"
android:visibility="invisible"/>
private Chronometer chronometerRecordTime;
chronometerRecordTime = findViewById(R.id.chronometerRecordTime);
chronometerRecordTime.setBase(SystemClock.elapsedRealtime()); // Reset
chronometerRecordTime.start(); // start
chronometerRecordTime.stop(); // stop
I have also crate timer to stop recording after one min. you can
modify it according to your requirement.
int myTimeCounter;
Timer myRecordingTimer;
private boolean myTimerHasStarted = false;
private String TAG = "Log";
private void startTimerTask() {
myTimeCounter = 1;
myRecordingTimer = new Timer();
myRecordingTimer.scheduleAtFixedRate(new TimerTask() {
public void run() {
runOnUiThread(new Runnable() {
public void run() {
myTimerHasStarted = true;
if (myTimeCounter == 60) {
myRecordingTimer.cancel();
myTimerHasStarted = false;
return;
}
Log.d(TAG, "timer=" + String.valueOf(myTimeCounter));
myTimeCounter++;
}
});
}
}, 0, 1000);
}

how to make program read stopwatch and then print statement in another textview box when time reaches that second

I want to make a stopwatch. when my stopwatch reaches 1 minute I want it to print a statement, how can i make it do this?
I am using android studio(java), Here is a bit of my code:
Button btnStart,btnPause,btnLap;
TextView txtTimer;
Handler customHandler = new Handler();
LinearLayout container;
TextView lt;
long startTime=0L,timeinMilliseconds=0L,timeSwapBuff=0L,updateTime=0L;
Runnable updateTimerThread = new Runnable() {
#Override
public void run() {
timeinMilliseconds = SystemClock.uptimeMillis() -startTime;
updateTime = timeSwapBuff+timeinMilliseconds;
int secs=(int) (updateTime/1000);
int mins=secs/60;
secs%=60;
int milliseconds=(int) (updateTime%1000);
String s = "" + mins + ":" + String.format("%02d",secs) + ":" + String.format("%03d",milliseconds);
txtTimer.setText (s);
customHandler.postDelayed(this,0);
}
};
If you just want to setText after some X minutes just create a method like this:
private void printText(int minutes) {
new Handler().postDelayed(new Runnable() {
#Override
public void run() {
//do you setText here
}
}, minutes * 1000);
}
and use it like:
printText(1);
Update:
Chronometer is exactly what you are looking for.
It extends TextView, so just replace your timer textview with Chronometer
mChronometer = findViewById(R.id.chronometer2);
mChronometer.setBase(SystemClock.elapsedRealtime());
mChronometer.start();
mChronometer.setOnChronometerTickListener(new Chronometer.OnChronometerTickListener() {
#Override
public void onChronometerTick(Chronometer chronometer) {
long elapsedMillis = SystemClock.elapsedRealtime() - mChronometer.getBase();
int secs = (int) (elapsedMillis/1000);
int mins = secs/60;
if (mins == 1) {
mChronometer.stop();
anotherTextVeiw.setText("the 1 minute mark has passed");
}
}
});
You don't have to deal with Handler and Runnable with this approach

Running a method every second starting on button press

I need a timer to start any time I press a button (on the button itself) that shows how many seconds it's been since it's pressed in real time. Whenever it's pressed again, timer is reset to 0 and starts incrementing again
I know this isn't the way to do it, the button works fine but the timer should be in onCreate? I'm not sure how this is supposed to work with a button
public class MainActivity extends Activity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
downloadedImg = (ImageView) findViewById(R.id.imageView);
}
public void clickAsync(View view) {
new ImageDownloader().execute(downloadUrl);
int seconds = 0;
Button button = (Button) view;
button.setText("Seconds since clicked: " + seconds);
Timer timer = new Timer();
//each time button is clicked, time is reset to 0 and increments in real time
timer.scheduleAtFixedRate(new TimerTask()
{
public void run()
{
seconds = 0;
seconds++;
button.setText("Seconds since clicked: " + seconds);
}
}, 0, 1000);
}
}
Another easy way to do this is to use Handler
mHandler = new Handler();
Just call updateSec();method on click of a button it'll update sec in interval of one seconds
Runnable UpdateRunnable = new Runnable() {
#Override
public void run() {
updateSec();
}
};
public void updateSec() {
mSeconds++;
mHandler.postDelayed(UpdateRunnable, 1000);
}
Example
button.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
mSeconds = 0;
updateSec();//it'll update sec variable every second.
}
});
try this: use a handler
long startTime = 0;
long elapsedTime ;
//runs without a timer by reposting this handler at the end of the runnable
Handler timerHandler = new Handler();
Runnable timerRunnable = new Runnable() {
#Override
public void run() {
long millis = System.currentTimeMillis() - startTime;
int seconds = (int) (millis / 1000);
int minutes = seconds / 60;
int hours = minutes / 60;
seconds = seconds % 60;
//textview for displaying time..
timerTextView.setText(String.format("%d:%02d:%02d", hours, minutes, seconds));
timerHandler.postDelayed(this, 1000);
}
};
b.setOnClickListener(new View.OnClickListener() { //b is your button
#Override
public void onClick(View v) {
Button b = (Button) v;
if (b.getText().equals("Stop")) {
elapsedTime = System.currentTimeMillis() - startTime;
timerHandler.removeCallbacks(timerRunnable);
b.setText("Resume");
} else {
startTime = System.currentTimeMillis() - elapsedTime;
timerHandler.postDelayed(timerRunnable, 0);
Calendar cs = Calendar.getInstance();
System.out.println("Current time => " + cs.getTime());
SimpleDateFormat df = new SimpleDateFormat("HH:mm");
String formattedDate = df.format(cs.getTime());
timerTextView.setText(formattedDate);
b.setText("Stop");
}
}
});
it will calculate the elapsed time and show time after stop...
You can use threads:
#Override
public void onClick(View view){
switch(view.getId()){
case R.id.button:
new Thread(new Runnable() {
#Override
public void run() {
try{
Thread.sleep(1000);
} catch(InterruptedException e) {
e.printStackTrace();
}
count++;
textView.post(new Runnable() {
#Override
public void run() {
textView.setText(count + "");
}
});
}
}
}).start;
break;
}
}
the view must be updated on main thread, and so you need to use post() method that has runnable instance as parameter.
Alternatively, you can also use AsyncTask.

Java/Android Countdown timer

i'm trying to make an countdown timer on Android with java. There are a timer a 25 minute study timer and a 5 minute break timer. I have both timers working. However, I don't know how to cancel/clear the timers. If I click I start a study timer and break timer they will both run simultaneously and I don't want that. I want the original timer to cancel when another timer is put on. This is the code.
btnStart.setOnClickListener(new OnClickListener() {
public void onClick(View v){
btnStart.setEnabled(false);
btnBreak.setEnabled(true);
breakBoolean = false;
CountDownTimer timer;
long amountOfStudyTime = 1500000; //30 seconds (may cause problems)
long countDownInterval = 1000; //1 second
//Initialise the countdown timer
timer = new CountDownTimer(amountOfStudyTime, countDownInterval){
public void onTick(long millisUntilFinished){
if( studyBoolean = false ) {
tViewTime.setText("CountDownTimer Canceled/stopped.");
cancel();
breakBoolean = true;
}else{
//display remaining seconds to user
tViewTime.setText(""+String.format("%d min, %d sec",
TimeUnit.MILLISECONDS.toMinutes( millisUntilFinished),
TimeUnit.MILLISECONDS.toSeconds(millisUntilFinished) -
TimeUnit.MINUTES.toSeconds(TimeUnit.MILLISECONDS.toMinutes(millisUntilFinished))));
}
}
public void onFinish(){
//When countdown is finished do...
breakBoolean = true;
int currentScore = Integer.parseInt(editScore.getText().toString());
int finalScore = currentScore + 5;
editScore.setText(Integer.toString(finalScore));
tViewTime.setText("Done");
}
}.start();
}
});
//Set a click listener for break button
btnBreak.setOnClickListener(new OnClickListener() {
public void onClick(View v){
btnStart.setEnabled(true);
btnBreak.setEnabled(false);
studyBoolean = false;
CountDownTimer timer2;
long amountOfBreakTime = 300000; //30 seconds (may cause problems)
long countDownInterval = 1000; //1 second
//Initialise the countdown timer
timer2 = new CountDownTimer(amountOfBreakTime, countDownInterval){
public void onTick(long millisUntilFinished){
if( breakBoolean = false ) {
cancel();
studyBoolean = true;
}else{
//display remaining seconds to user
tViewTime.setText(""+String.format("%d min, %d sec",
TimeUnit.MILLISECONDS.toMinutes( millisUntilFinished),
TimeUnit.MILLISECONDS.toSeconds(millisUntilFinished) -
TimeUnit.MINUTES.toSeconds(TimeUnit.MILLISECONDS.toMinutes(millisUntilFinished))));
}
}
public void onFinish(){
//When countdown is finished do...
tViewTime.setText("Done");
studyBoolean = true;
}
}.start();
}
});
Create two CountDownTimer objects in your activity and cancel them depending on your button selected :
public class MainActivity extends Activity {
boolean breakIsRunning = false;
boolean startIsRunning = false;
Button btnStart,btnBreak;
CountDownTimer startTimer = new CountDownTimer(amountOfStudyTime, countDownInterval)
{
#Override
public void onFinish() {
//do something
startIsRunning = false;
}
#Override
public void onTick(long arg0) {
//do something
startIsRunning = true;
}
};
CountDownTimer breakTimer = new CountDownTimer(amountOfBreakTime, countDownInterval)
{
#Override
public void onFinish() {
//do something
breakIsRunning = false;
}
#Override
public void onTick(long arg0) {
//do something
breakIsRunning = true;
}
};
//->OnCreate() - >Buttons code
btnStart.setOnClickListener(new OnClickListener().. { // your listener code here
if(breakIsRunning)
breakTimer.cancel();
startTimer.start();
}
btnBreak.setOnClickListener(new OnClickListener().. { //
if(startIsRunning)
startTimer.cancel();
breakTimer.start();
}
}

disable a thread on click

I am working on app that calculate time when specific app run, to save ram, I want to stop some of the threads by using check box. i want a command when I press the check box the thread stops even "if condition" is right"
the if conditon of detecting app :
if (MainActivity.tgbutton.isChecked())
{
if (packageName.equals("com.facebook.katana"))
{
if (f==1)
{
}
else
{
// Toast.makeText(getApplicationContext(),"fb on", Toast.LENGTH_SHORT).show();
f=1;
facebook = true;
startTimef = SystemClock.uptimeMillis();
customHandlerf.postDelayed(updateTimerThreadfacebook, 0);
}
}
else
{
if(f==1)
{
//Toast.makeText(getApplicationContext(),"fb off", Toast.LENGTH_SHORT).show();
facebook = false;
timeSwapBufff += timeInMillisecondsf;
customHandlerf.removeCallbacks(updateTimerThreadfacebook);
f=2;
}
}
}
the check box :
blabla.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
if (((CheckBox) v).isChecked()) {
// what to write here to disable thread???
}
}
});
the thread itself :
private Runnable updateTimerThreadfacebook = new Runnable() {
public void run() {
if (facebook = true)
{
timeInMillisecondsf = SystemClock.uptimeMillis() - startTimef;
updatedTimef = timeSwapBufff + timeInMillisecondsf;
int secsf = (int) (updatedTimef / 1000);
int minsf = secsf / 60;
secsf = secsf % 60;
MainActivity.facebook.setText("" + minsf + ":" + String.format("%02d", secsf));
customHandlerf.postDelayed(this, 0);
}
}
};
you should use value on your run method
public class MyClass implements Runnable{
boolean signal=false;
public setisFinish(boolean sig)
{
signal = sig;
}
#Override
public void run()
{
if(!signal)
//Do SomeThing
}
public void foo()
{
System.out.println("foo");
}
}
and in your click listener
blabla.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
if (((CheckBox) v).isChecked()) {
myThread.setisFinish(true);
}
}
});
this code resume your thread and you can start it whenever you whant and if you want interrupt your thread use this code
myThread.interrupt();
Overwrap your Runnable object with Thread class:
private Thread updateTimerThreadfacebook = new Thread(new Runnable() {
public void run() {
if (facebook = true) {
timeInMillisecondsf = SystemClock.uptimeMillis() - startTimef;
updatedTimef = timeSwapBufff + timeInMillisecondsf;
int secsf = (int) (updatedTimef / 1000);
int minsf = secsf / 60;
secsf = secsf % 60;
MainActivity.facebook.setText("" + minsf + ":" + String.format("%02d", secsf));
customHandlerf.postDelayed(this, 0);
}
}
});
when you want to stop it use interrupt method.
updateTimerThreadfacebook.interrupt();

Categories