I am working on android applications. In my project I have 3 pages.
The first page consists of 1 button.
The second page is consists of the timer code.
The third page consists of again a button.
Now my requirement is when I click on the first page button the third page should open and the timer in second page should pause. Again when I click on the third page button
the second page timer should restart the time where it is stopped and should open the first page.
I am struggling to achieve this task.Guide me through it, Suggest what should have been done to do that.
Page1.java
rowTextView.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
Intent myIntent = new Intent(v.getContext(),Page3.class);
startActivity(myIntent);
finish();
}
});
Page2.java
public class TimeractivitybestActivity extends Activity {
EditText e1;
MyCount counter;
Long s1;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
e1 = (EditText) findViewById(R.id.editText1);
counter = new MyCount(15000, 1000);
counter.start();
}
public void method(View v) {
switch (v.getId()) {
case R.id.button1:
counter.cancel();
break;
case R.id.button2:
counter = new MyCount(s1, 1000);
counter.start();
}
}
public class MyCount extends CountDownTimer {
public MyCount(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
}
#Override
public void onFinish() {
e1.setText("DONE");
}
#Override
public void onTick(long millisUntilFinished) {
s1 = millisUntilFinished;
e1.setText("left:" + millisUntilFinished / 1000);
}
}
}
Page3.java
public void gobacktopage1(View v)
{
Intent myIntent = new Intent(v.getContext(),Page1.class);
startActivity(myIntent);
finish();
}
You can always store the timeLeft which is s1 and use it again like this, Read the comments too
1) While calling timer,check if you have any stored time
Page1.java
rowTextView.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
SharedPreferences sp = PreferenceManager.getDefaultSharedPreferences(this);
long time = sp.getLong("time", 0); // get saved time of times
Intent myIntent = new Intent(v.getContext(),Page3.class);
myIntent.putExtra("time", time); // send it to page2
startActivity(myIntent);
finish();
}
});
2) Use the time to start time if it's not 0.
Page2.java
public class TimeractivitybestActivity extends Activity {
EditText e1;
MyCount counter;
Long s1;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
long time = this.getIntent().getLongExtra("time", 0); // get
// saved
// time
time = (time != 0) ? time : 1500;
e1 = (EditText) findViewById(R.id.editText1);
counter = new MyCount(time, 1000); // start with saved time
counter.start();
}
public void method(View v) {
switch (v.getId()) {
case R.id.button1:
counter.cancel();
break;
case R.id.button2:
counter = new MyCount(s1, 1000);
counter.start();
}
}
public class MyCount extends CountDownTimer {
public MyCount(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
}
#Override
public void onFinish() {
e1.setText("DONE");
}
#Override
public void onTick(long millisUntilFinished) {
s1 = millisUntilFinished;
e1.setText("left:" + millisUntilFinished / 1000);
}
}
public void onPause() {
SharedPreferences sp = PreferenceManager
.getDefaultSharedPreferences(this);
Editor et = sp.edit();
et.putLong("time", s1); // save time SharedPreference in onPause
et.commit();
}
}
3) no change in page 3, I suppose.
Page3.java
public void gobacktopage1(View v)
{
Intent myIntent = new Intent(v.getContext(),Page1.class);
startActivity(myIntent);
finish();
}
public class TimerActivity extends Activity{
EditText e1;
MyCount counter;
Long s1;
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
e1=(EditText)findViewById(R.id.editText1);
counter= new MyCount(5000,1000);
counter.start();
}
public void asdf(View v)
{
switch(v.getId())
{
case R.id.button1: counter.cancel();
break;
case R.id.button2: counter= new MyCount(s1,1000);
counter.start();
}
}
public class MyCount extends CountDownTimer
{
public MyCount(long millisInFuture, long countDownInterval)
{
super(millisInFuture, countDownInterval);
}
#Override public void onFinish()
{
e1.setText("DONE");
}
#Override public void onTick(long millisUntilFinished)
{
s1=millisUntilFinished;
e1.setText("left:"+millisUntilFinished/1000);
}
}
}
this is how it works...
MyCount counter;
Long s1;
counter= new MyCount(300000,1000);
counter.start();
public void asdf(View v){ <---- method for onclick of buttons pause and resuming timer
switch(v.getId()){
case R.id.button1:<-- for pause
counter.cancel();
break;
case R.id.button2:<--- for resume
counter= new MyCount(s1,1000);
counter.start();
}
}
public class MyCount extends CountDownTimer{
public MyCount(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
}
#Override
public void onFinish() {
mediaplayer.stop();
mediaplayer.release();
}
#Override
public void onTick(long millisUntilFinished) {
s1=millisUntilFinished;
}
}
case R.id.button1:<-- for pause
counter.cancel();
this the one which is used to pause the timer and start again...
and in ur case
public void gobacktopage1(View v)
{
Intent myIntent = new Intent(v.getContext(),Page1.class);
startActivity(myIntent);
finish();
}
write a method in that add counter.cancel(); in that method and call that method...
Related
I have class MainActivity below, I need to cancel the counting down on method onBackPressed from other class. I also copied the CountDownTimer class below. How do I do it properly, any help? Thank you for reply.
#Override
public void onCreate(Bundle savedInstanceState) {
textViewTime = (TextView) findViewById(R.id.tv_Time);
textViewTime.setText(getString(R.string.countdown_time));
final CounterClass timer = new CounterClass(10999, 900);
timer.start();
btnStop.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
timer.cancel();
}
});
}
#Override
public void onBackPressed() {
super.onBackPressed();
// here cancel //
}
public class CounterClass extends CountDownTimer {
public CounterClass(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
}
#Override
public void onFinish() {
textViewTime.setText("COMPLETED");
}
#Override
public void onTick(long millisUntilFinished) {
long millis = millisUntilFinished;
String hms = String.format("%02d:%02d:%02d", TimeUnit.MILLISECONDS.toHours(millis),
TimeUnit.MILLISECONDS.toMinutes(millis) - TimeUnit.HOURS.toMinutes(TimeUnit.MILLISECONDS.toHours(millis)),
TimeUnit.MILLISECONDS.toSeconds(millis) - TimeUnit.MINUTES.toSeconds(TimeUnit.MILLISECONDS.toMinutes(millis)));
textViewTime.setText(hms);
}
}
CountDownTimer has a cancel() method that can be called to terminate the timer.
Your MainActivity would look like this
public class MainActivity extends Activity {
private final CounterClass timer;
#Override
public void onCreate() {
timer = new CounterClass(10999, 900);
timer.start();
/* rest of the code omitted */
}
#Override
public void onBackPressed() {
super.onBackPressed();
timer.cancel()
}
}
I am trying to make a simple quiz for practicing. I have problem adding a countdown timer. It works fine if no question is answered, but when I answer a question (even if it is correct or wrong), the timer doesn't reset. I saw on developer.android.com that there is the method cancel(), but I cannot make it work. Any help?
Here is my code. (Any suggestion for better code is welcome, but I try to keep it simple cause I am new to android development).
public class QuizActivity extends Activity implements OnClickListener{
int MAX_Q = 6;
List<Question> quesList;
int score=0;
int lives=3;
int qid=0;
Question currentQ;
TextView txtQuestion, TextViewTime;
Button ansA, ansB, ansC;
private MediaPlayer mpCorrect;
private MediaPlayer mpWrong;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_quiz);
DbHelper db=new DbHelper(this);
quesList=db.getAllQuestions();
currentQ=quesList.get(qid);
txtQuestion=(TextView)findViewById(R.id.questionTextView);
ansA = (Button)findViewById(R.id.ans1);
ansB=(Button)findViewById(R.id.ans2);
ansC=(Button)findViewById(R.id.ans3);
ansA.setOnClickListener(onClickListener);
ansB.setOnClickListener(onClickListener);
ansC.setOnClickListener(onClickListener);
mpCorrect = MediaPlayer.create(this, R.raw.correct);
mpWrong = MediaPlayer.create(this, R.raw.wrong);
setQuestionView();
}
public class CounterClass extends CountDownTimer{
public CounterClass(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
// TODO Auto-generated constructor stub
}
#Override
public void onTick(long millisUntilFinished) {
long millis = millisUntilFinished;
String secs = String.format("00:%02d", TimeUnit.MILLISECONDS.toSeconds(millis));
TextViewTime.setText(secs);
}
#Override
public void onFinish() {
wrongAnswer();
}
}
private OnClickListener onClickListener = new OnClickListener() {
#Override
public void onClick(final View v) {
switch(v.getId()){
case R.id.ans1:
if(currentQ.getANSWER().equals(ansA.getText()))
correctAnswer();
else
wrongAnswer();
break;
case R.id.ans2:
if(currentQ.getANSWER().equals(ansB.getText()))
correctAnswer();
else
wrongAnswer();
break;
case R.id.ans3:
if(currentQ.getANSWER().equals(ansC.getText()))
correctAnswer();
else
wrongAnswer();
break;
}
}
};
private void setQuestionView()
{
txtQuestion.setText(currentQ.getQUESTION());
ansA.setText(currentQ.getOPTA());
ansB.setText(currentQ.getOPTB());
ansC.setText(currentQ.getOPTC());
qid++;
showLives();
showScore();
TextViewTime=(TextView)findViewById(R.id.TextViewTime);
TextViewTime.setText("00:10");
final CounterClass timer = new CounterClass(10000, 1000);
timer.start();
}
private void showLives()
{
TextView c=(TextView)findViewById(R.id.lives);
c.setText(String.valueOf(lives));
}
private void showScore()
{
TextView d=(TextView)findViewById(R.id.score);
d.setText(String.valueOf(score));
}
private void gameOver() {
Intent intent = new Intent(QuizActivity.this, ResultActivity.class);
Bundle b = new Bundle();
b.putInt("score", score);
intent.putExtras(b);
Bundle c = new Bundle();
intent.putExtras(c);
startActivity(intent);
finish();
}
private void correctAnswer() {
score+=10;
Log.d("score", "Your score"+score); // log gia to score
mpCorrect.start();
checkGame();
}
private void wrongAnswer() {
--lives;
Log.d("lives", "Your lives"+lives);
score-=2;
Log.d("score", "Your score"+score);
if (score<0)
score=0;
mpWrong.start();
checkGame();
}
private void checkGame(){
if(qid<MAX_Q && lives>0){
currentQ=quesList.get(qid);
setQuestionView();
}
else
gameOver();
}
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
}
}
Your QuizActivity doesn't need to implement OnClickListener + OnClick, as your custom OnClickListener already does that part.
To your actual question:
First, declare your CounterClass variable class-wide.
At the moment, you make a new variable called timer every time your setQuestionView is called and destroy the reference (not the object it self) every time the method finishes, as it is an auto-variable, only living as long as the method it's created by.
Second, using your now usable timer reference, reset the timer.
In the OnClick of your custom OnClickListener, before checking the answer, stop your timer using timer.cancel();.
In your setQuestionView, in the end of it not only start the timer, but also make a new one, so you got a new timer with the full 10 seconds and the old one may get GC'd (if it doesn't get destroyed by cancel() anyway; I haven't got the IDE here so I can't code crawl).
Your new setQuestionView():
private void setQuestionView()
{
txtQuestion.setText(currentQ.getQUESTION());
ansA.setText(currentQ.getOPTA());
ansB.setText(currentQ.getOPTB());
ansC.setText(currentQ.getOPTC());
qid++;
showLives();
showScore();
TextViewTime=(TextView)findViewById(R.id.TextViewTime);
TextViewTime.setText("00:10");
timer = new CounterClass(10000, 1000);
timer.start();
}
Here is an example that may help you understand how the cancel() works.
public class TestTimer extends Activity
{
private final int START_TIME = 10000;
TextView TextViewTime;
CounterClass timer = null;
long millis = START_TIME;
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_quiz);
TextViewTime = (TextView) findViewById(R.id.textViewTime);
setTime();
Button buttonStart = (Button) findViewById(R.id.buttonStart);
Button buttonStop = (Button) findViewById(R.id.buttonStop);
Button buttonReset = (Button) findViewById(R.id.buttonReset);
buttonStart.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v)
{
timer = new CounterClass(millis, 1000);
timer.start();
}
});
buttonStop.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
timer.cancel();
}
});
buttonReset.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
millis = START_TIME;
setTime();
}
});
}
public class CounterClass extends CountDownTimer {
public CounterClass(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
}
#Override
public void onTick(long millisUntilFinished) {
millis = millisUntilFinished;
setTime();
}
#Override
public void onFinish() {
setTime();
}
}
public void setTime() {
String secs = String.format("00:%02d", TimeUnit.MILLISECONDS.toSeconds(millis));
TextViewTime.setText(secs);
}
}
And the trivial layout:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<TextView
android:id="#+id/textViewTime"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="" />
<Button
android:id="#+id/buttonStart"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="start" />
<Button
android:id="#+id/buttonStop"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="stop" />
<Button
android:id="#+id/buttonReset"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="reset" />
</LinearLayout>
Here I have 3 activities: A, B, and C. From Activity A When I click a button it will goes to Activity B. When Activity B loads the countdown timer will start. Again, when I click a button in Activity B it will go to Activity C. Here I Need a Help.
When Activity C starts I need the countdown timer from Activity B to resume.
Again I switch over from Activity C to Activity B the countdown timer should be resumed from Activity C.
Activity A
public class MainActivity extends Activity {
Button button;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
addListenerOnButton();
}
public void addListenerOnButton() {
final Context context = this;
button = (Button) findViewById(R.id.actone);
button.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View arg0) {
Intent intent = new Intent(context, Act_Two.class);
startActivity(intent);
}
});
}
}
Activity B
public class Act_Two extends Activity{
Button button;
public TextView textView1;
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.act_two);
textView1=(TextView) findViewById(R.id.textView1);
MyCount counter = new MyCount(61000,1000);
counter.start();
addListenerOnButton();
}
public void addListenerOnButton() {
final Context context = this;
button = (Button) findViewById(R.id.acttwo);
button.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View arg0) {
Intent intent = new Intent(context, Act_Three.class);
startActivity(intent);
}
});
}
public class MyCount extends CountDownTimer{
public MyCount(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
}
//iFallApp app1 = new iFallApp();
#Override
public void onFinish() {
// TODO Auto-generated method stub
setContentView(R.layout.activity_main);
//textView1.setText("done");
}
#Override
public void onTick(long millisUntilFinished) {
// TODO Auto-generated method stub
textView1.setText(Long.toString(millisUntilFinished/1000));
}
}
}
While switching between the activities, try to pass the current count down time with the help of Bundle.
You should save a value of your CountDownTimer in Activty B and stop the CountDownTimer (using the cancel() method) in Activty B's onPause and start that CountDownTimer with saved value in onResume of Activty B. something like (assuming this is an Activity B code):
#Override
public void onPause() {
// turning off the timer
isWihesCountUpdateTimerNeeded = false;
if (wihesCountUpdateTimer!=null)
wihesCountUpdateTimer.cancel();
super.onPause();
}
#Override
public void onResume() {
super.onResume();
// resuming the timer
isWihesCountUpdateTimerNeeded = true;
totalWishesCount = SharedPrefsHelper.getTotalWishesCount(getActivity());
startWihesCountUpdateTimer();
}
// the timer increases some wishes count
private boolean isWihesCountUpdateTimerNeeded;
private CountDownTimer wihesCountUpdateTimer;
protected static final int wihesCountUpdateTimerDuration=5000;
protected int totalWishesCount;
private void startWihesCountUpdateTimer() {
wihesCountUpdateTimer = null;
if (!isWihesCountUpdateTimerNeeded)
return;
final int duration = wihesCountUpdateTimerDuration;
//Log.i(this, "startWihesCountUpdateTimer() duration: "+duration);
wihesCountUpdateTimer = new CountDownTimer(duration, 1000) {
#Override
public void onTick(long millisUntilFinished) {}
#Override
public void onFinish() {
totalWishesCount++;
SharedPrefsHelper.saveTotalWishesCount(getActivity(), totalWishesCount);
startWihesCountUpdateTimer();
}
}.start();
}
I created a countdown timer with a good loocking output in mm:ss
So if I switch to the activityView befor and come back to the activity with the timer, everything looks good but;-):
timer is still running in the background - but it looks vergin, no counting..
at this way I can start a second, third,... timer, because the button is already active
So I know that I have to set all these settings, and that it is quite normal. I have to set the
startButon to disable - while counter runs...
refresh the activityView if the user come back and the counter is still sctive
Maybe you can show me haw to do that for ANDROID? Herey my working code:
some imports....
public class BasicActivity extends Activity {
ImageButton start, stop;
TextView timer;
/** Called when the activity is first created. */
//Ist dei Verbindung zur XML
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.basic_activity);
//TIMER
start = (ImageButton)findViewById(R.id.startButton);
stop = (ImageButton)findViewById(R.id.stopButton);
timer = (TextView)findViewById(R.id.basicCountDown);
timer.setText(getString(R.string.basic01)); // Platzhalter im Textfeld.
final MyCounter timer = new MyCounter(10000,1000);
start.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
timer.start();
}
});
stop.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
timer.cancel();
}
});
}
public class MyCounter extends CountDownTimer{
public MyCounter(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
}
#Override
public void onFinish() {
System.out.println("Timer Completed.");
timer.setText(getString(R.string.basic02));
//Spielt den TON ab, wenn die ZEit um ist. Siehe Methode playSound!
playSound();
//Notification
new AlertDialog.Builder(BasicActivity.this).setTitle(getString(R.string.app_name)).setMessage(getString(R.string.basicNotificationMessage)).setIcon(R.drawable.ic_launcher).setNeutralButton(getString(R.string.ButtonOK), null).show();
}
#Override
public void onTick(long millisUntilFinished) {
SimpleDateFormat dateFormat = new SimpleDateFormat("mm:ss");
// dateFormat.setTimeZone(TimeZone.getTimeZone("GMT"));
Date date = new Date(millisUntilFinished);
timer.setText(dateFormat.format(date));
// System.out.println("Timer : " + (millisUntilFinished/1000));
System.out.println("Timer : " + dateFormat.format(date));
}
}
//Sound nach Ablauf der Zeit
public void playSound() {
final MediaPlayer mp = MediaPlayer.create(getApplicationContext(), R.raw.ton_timer);
mp.start();
}
}
1.
start.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
v.setEnabled(false);
timer.start();
}
});
stop.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
timer.cancel();
start.setEnabled(true)
}
});
#Override
public void onFinish() {
System.out.println("Timer Completed.");
timer.setText(getString(R.string.basic02));
start.setEnabled(true);
//Spielt den TON ab, wenn die ZEit um ist. Siehe Methode playSound!
playSound();
//Notification
new AlertDialog.Builder(BasicActivity.this).setTitle(getString(R.string.app_name)).setMessage(getString(R.string.basicNotificationMessage)).setIcon(R.drawable.ic_launcher).setNeutralButton(getString(R.string.ButtonOK), null).show();
}
refresh the activityView if the user come back and the counter is
still sctive
That's a bit tricky. Surely If you leave the Activity you should cancel the CountDownTimer or your Activity could be leak.
I'm trying to start a new activity "SMS.java", if I dont respond to my timer within 30secs. After 30secs, the new ativity should be started. Can anyone help me out??? The class Timer on line 5 extends a CountDownTimer..
Here's the code:
//TimerAct.java
public class TimerAct extends Activity
{
static TextView timeDisplay;
Timer t;
int length = 30000;
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.time);
timeDisplay = (TextView) findViewById(R.id.timer);
timeDisplay.setText("Time left: " + length / 1000);
t = new Timer(length, 1000);
t.start();
View b1 = findViewById(R.id.abort);
b1.setOnClickListener(new View.OnClickListener()
{
public void onClick(View v)
{
t.cancel();
finish();
}
});
}
}
//Timer.java
public class Timer extends CountDownTimer
{
public Timer(long millisInFuture, long countDownInterval)
{
super(millisInFuture, countDownInterval);
}
public void onTick(long millisUntilFinished)
{
TimerAct.timeDisplay.setText("Time left: " + millisUntilFinished / 1000);
}
public void onFinish()
{
TimerAct.timeDisplay.setText("Time over!!!");
}
}
For a timer method, better you can use with threading. It will work.
This is the example for Show Timer in android using threads. It runs the thread every second. Change the time if you want.
Timer MyTimer=new Timer();
MyTimer.schedule(new TimerTask() {
#Override
public void run() {
runOnUiThread(new Runnable() {
public void run() {
TimerBtn=(Button) findViewById(R.id.Timer);
TimerBtn.setText(new Date().toString());
}
});
}
}, 0, 1000);
What I do is call a method from the Activity on my CountDownTimer class, like this:
//Timer Class inside my Activity
public class Splash extends CountDownTimer{
public Splash(long millisInFuture, long countDownInterval) {
super(millisInFuture, countDownInterval);
}
#Override
public void onFinish() {
nextActivity(Login.class, true);
}
#Override
public void onTick(long millisUntilFinished) {}
}
//Method on my Activity Class
protected void nextActivity(Class<?> myClass, boolean finish) {
Intent myIntent = new Intent(this, myClass);
myIntent.addFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
startActivity(myIntent);
if(finish)
finish();
}