Quick question here, I have the following code working for the most part, but I would like for the button to go back to it's original state if it is clicked during the countdown. Any suggestions?
button.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
new CountDownTimer(4000, 1000) {
#Override
public void onFinish() {
button.setText("SENT");
}
#Override
public void onTick(long sec) {
button.setText("CANCEL (" + sec / 1000 + ")");
button.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
cancel();
}
});
}
}.start();
}
});
Before the button is ever pressed, it will say "Push Me." Once pressed, the countdown will begin and the button's text will change each second (CANCEL (3), CANCEL (2), CANCEL (1)) and after the countdown the button will update its text to "SENT." If the button is pressed during the countdown (onTick), it will cancel the countdown. I would like to know how to make it revert to the "Push Me" state, and basically allow it to be pressed again and begin a new countdown. Any help would be appreciated!
So you should not have a new onClickListener inside of the timer because that uses a lot more memory then is needed, and may cause unexpected results. Instead I would suggest using a boolean value for if the timer is on, and use your existing button's onClickListener. Make sure that your timer is declared globally if you are using this. Here is an example of how that might work:
button.setOnClickListener(new OnClickListener {
if(timerIsOn){
if(timer != null){
timer.cancel();
timerIsOn = false;
}
}
else{
timerIsOn = true;
//start the timer and do whatever else
}
}
Related
I am designing a simple app in which myfunction() is called when the start button is pressed. myfunction() takes a few seconds to complete. Right now when I press the Start Button, myfunction() runs for a few seconds and after it is complete, the text of the button changes to "Stop". I want the text of the button to change to "Stop" as soon as the "Start" Button is pressed and before the function is called.
This is my first time working with Android Studio and Java. Any help is appreciated.
I've attached the function which is called when the button is pressed.
public void buttonClick(View v) {
Button tv = (Button)findViewById(R.id.button1);
if(tv.getText() == "Start") {
tv.setText("Stop");
myfunction();
}
else {
tv.setText("Start");
}
}
Don't use tv.getText()=="Start" use tv.getText().equals("Start") like this...
public void buttonClick(View v) {
Button tv = (Button)findViewById(R.id.button1);
if(tv.getText().equals("Start")) {
tv.setText("Stop");
myfunction();
}
else {
tv.setText("Start");
}
}
to use the equals, do something like :
public void buttonClick(View v) {
Button tv = (Button)findViewById(R.id.button1);
if(tv.getText().toString() == "Start") {
tv.setText("Stop");
myfunction();
}
else {
tv.setText("Start");
}
}
I am making an android app. Here's what I want: User clicks a button, button text changes to "xyz", and then the program waits for 1 second and then the button text changes to "abc".If I use Thread.sleep(1000) then the program does stop for a second but the button text doesn't change to "xyz" before the program goes to sleep.
You can use Handler to achieve this. Using postdelayed method you can do this. Below is the code to do this
button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
button.setText("xyz"); // text changed to xyz
new Handler().postDelayed(new Runnable() {
#Override
public void run() {
button.setText("abc"); //text changed to abc after 1 second.
}
},1000);
}
});
Sorry for the terrible title, I am bad at describing these things.
I am building a metronome and have a (-) UI button that decreases the tempo by 1, and a (+) UI button that increases the tempo by 1.
My problem currently is that whenever I press either buttons, the metronome restarts itself since there's a new tempo, and plays immediately. So if you press the (-) button 10 times in a row, each time you press it you hear the initial metronome "beep".
I would like my app to do the following:
When the user clicks either (-) or (+) buttons, wait for 200 milliseconds
IF the user didn't click the buttons again in that timeframe, play the metronome
If the user DID click the button again, don't play the metronome, repeat the process: wait 200 milliseconds, if no click was made play the metronome, etc
The end result would be that if I'm at 100 bpm and I repeatedly press the (+) button 20 times until I am at 120 bpm, the metronome wouldn't start playing until I am done tapping.
How do I go about implementing this? Thank you!
Declare and instantiate the below in your activity:
private Handler timeoutHandler = new Handler();
private Runnable delayStartThread = new Runnable() {
public void run() {
startMetronome();
}
};
Then insert the below code block in your onClickListener for both + and - buttons:
button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
timeoutHandler.removeCallbacks(delayStartThread);
tempoOfMetronome++; //tempoOfMetronome--; for decrease button
stopMetronome();
timeoutHandler.postDelayed(delayStartThread, 200);
}
});
For more details on how the code works, refer the below links for examples (I used these examples to formulate the answer):
Android: clicking TWICE the back button to exit activity - How to use handler.postDelayed()
How to cancel handler.postDelayed? - How to cancel handler.postDelayed()
You should also look at the Android documentation for those methods.
If you want a delay between the action and the effect, there are several ways you can achieve it. This is one.
private boolean pressedAction = false;
#override
public void onClick(View v) {
if (pressedAction) return;
pressedAction = true;
new Thread(new Runnable(
#override
public void run() {
try {
Thread.sleep(200); // 200 miliseconds
} catch (Exception e) {}
// Update views or do work (program logic)
pressedAction = false;
}
}
}
Then, the metronome logic is your bussiness.
I need to perform an action after onClick method of OnClickListener has run.
Here is my code for onClickListener:
View.OnClickListener imgButton0Handler0 = new View.OnClickListener() {
int identifier=0;
public void onClick(View v) {
//check if tile is found and return if it is
if(isFound[identifier]==true) return;
//set tile as open
checkField[identifier]=1;
//set background on predetermined
button0.setBackgroundResource(tiles[identifier]);
}
};
After this has run, and the background is set I would like to call a method checker(int identifier) which will check for other open tiles and change backgrounds accordingly.
This method needs to be run separately because the background is only displayed after onClick finishes, and I need predetermined background shown for a short time before checker method changes it to something else.
How can I accomplish this?
Have You Tried Post Delayed see this,
View.OnClickListener imgButton0Handler0 = new View.OnClickListener() {
int identifier=0;
public void onClick(View v) {
//check if tile is found and return if it is
if(isFound[identifier]==true) return;
//set tile as open
checkField[identifier]=1;
//set background on predetermined
button0.setBackgroundResource(tiles[identifier]);
new Handler().postDelayed(new Runnable() {
#Override
public void run() {
// This method will be executed once the timer is over
// Start your app main activity
checker(identifier) // your method call
}
}, 3000); // 3 second
}
};
I'm trying to build a SMS application that sends a SMS with one press on a button, this part is working but now I'm trying to implement a spam protection.
The spam protection means that you only can send 1 SMS per 10 seconds (or higher).
I've tried this:
sentSMS.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
Timer timer = new Timer();
int seconds = 10000;
timer.schedule(new TimerTask() {
public void run() {
processClick();
}
}, seconds);
}});
But this is not working when I press the button twice the SMS is also sending twice.
Maybe it's also a idea to make a toast which contains how many seconds the user have to wait, something like this:
Toast.makeText(getBaseContext(), "Spam protection, wait "+secondstowait,
Toast.LENGTH_SHORT).show();
Is this all possible to make?
why dont you just take a timestamp when the button was first clicked then compare the time when the button was clicked again and see if the difference is greater than the allotted amount of time?
Potentially, the easier thing to do in my opinion is to disable the button, and use the built-in handler (on the view object) to re-enable the button.
sentSMS.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
final View view = v;
v.setEnabled(false);
v.postDelayed(new Runnable(){
public void run(){
view.setEnabled(true);
}
}, 1000*10);
}});
You need to store when the button was last clicked and then see if 10 seconds have passed.
long lastTimeSent = 0; //start at 0
sentSMS.setOnClickListener(new OnClickListener() {
public void onClick(View v) {
if(System.currentTimeMillis() > lastTimeSent + 10000){ //if at least 10 secs has passed from last click
processClick();
lastTimeSent = System.currentTimeMillis(); //last time sent is now current time
}else{
Toast.makeText(getBaseContext(), "Spam protection, please wait.",
Toast.LENGTH_SHORT).show();
}
}});
if you want to show a toast message to user, notifying him about how many seconds are left,
you must write the toast.maketext code inside the timer schedule event too
using timestamp will not be easier way, rather it will make task more difficult.
You can also try to disable the button onclick for ten seconds and re-enable it after the time period is expired.