So Im trying to make a simple Tip Calculator as my first app. I watched multiple tutorials, but for some reason, I cant get the buttons to work. The slider works fine so Im not sure what the issue is.
From what I understand, this is where I setup each button threw an array.
int idList[] = {R.id.button1,R.id.button2,R.id.button3,
R.id.button4,R.id.button5,R.id.button6,
R.id.button7,R.id.button8,R.id.button9,
};
for (int id:idList){
View v = (View) findViewById(id);
v.setOnClickListener(btnClick);
}
and here is where I use them
private class ButtonclickListener implements View.OnClickListener{
public void onClick (View v) {
switch (v.getId()){
case R.id.buttonC: //clear
Scr.setText("0");
NumberBf = 0;
break;
case R.id.button_tip:
CalcTip();
break;
default:
String numb = ((Button) v).getText().toString();
getKeyboard(numb);
break;
}
}
}
In your list, you are using R.id.button1
But in your switch case you are using different IDs (R.id.buttonC)?
it should be
int idList[] = {R.id.button1,R.id.button2,R.id.button3,
R.id.button4,R.id.button5,R.id.button6,
R.id.button7,R.id.button8,R.id.button9,
};
for (int id:idList){
View v = (View) findViewById(id);
v.setOnClickListener(btnClick);
}
case R.id.button1: break; case R.id.button2: break;
In short when it should match when you do listener and findviewbyID
Related
HELP ME PLEASE! I want to create 2 buttons ("Next" and "Previous") that will change the text in TextView. I made a switch and "systemcounter" to change the cases, which then will set another text in TextView. When I test my program in this window buttons do not change the pages. I think this is because the system cannot see the "systemcounter"
private Button next_button;
private Button previous_button;
private TextView Text_set1;
int systemcounter = 0;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_learningpage);
next_button = (Button) findViewById(R.id.next_button);
previous_button = (Button) findViewById(R.id.previous_button);
Text_set1 = (TextView) findViewById(R.id.Text_set);
next_button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
systemcounter = systemcounter + 1;
}
});
previous_button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
systemcounter = systemcounter - 1;
}
});
switch (systemcounter) {
case (0):
Text_set1.setText("Thermodynamics is the branch of physics that deals with the relationships between heat and other forms of energy.");
previous_button.setVisibility(View.INVISIBLE);
break;
case (1):
Text_set1.setText("Hi there");
previous_button.setVisibility(View.VISIBLE);
break;
case (2):
Text_set1.setText("How are you");
previous_button.setVisibility(View.VISIBLE);
break;
case (3):
Text_set1.setText("How old are you?");
break;
default:
Text_set1.setText("OPS");
break;
}```
you have switch statement in oncreate method and so it executes it only once, make a seperate method like
setEditText(int systemcount) and create your switch tehre and call this methods from button onclick methods
private void setText() {
switch (systemcounter) {
case (0):
Text_set1.setText("Thermodynamics is the branch of physics that deals with the relationships between heat and other forms of energy.");
previous_button.setVisibility(View.INVISIBLE);
break;
case (1):
Text_set1.setText("Hi there");
previous_button.setVisibility(View.VISIBLE);
break;
case (2):
Text_set1.setText("How are you");
previous_button.setVisibility(View.VISIBLE);
break;
case (3):
Text_set1.setText("How old are you?");
break;
default:
Text_set1.setText("OPS");
break;
}
}
and call this method in your listeners (like this)
next_button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
systemcounter = systemcounter + 1;
setText();
}
});
I have three functions in my Main class, onCreate,onClick and click, I have two options, declare TextViews and some other views at the beginning of the project as global variables, which means they will stay in the entire app lifetime, or get them separately in each function(will cause the computer to work a bit more but the variables will not stay in memory the whole time). To describe the question further:
OPTION 1:
public static final int L = 6;
TextView[] textViews = new TextView[L];
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Random rand = new Random();
int[] digits = {rand.nextInt(10), rand.nextInt(10), rand.nextInt(10), rand.nextInt(10), rand.nextInt(10), rand.nextInt(10)};
for (int i = 0; i < L; i++) {
textViews[i] = (TextView) findViewById(getResources().getIdentifier("num" + String.valueOf(i), "id", getPackageName()));
textViews[i].setOnClickListener(this);
textViews[i].setText(String.valueOf(digits[i]));
}
}
#Override
public void onClick(View view) {
int id = view.getId();
switch (id) {
case R.id.num0:
click(0);
break;
case R.id.num1:
click(1);
break;
case R.id.num2:
click(2);
break;
case R.id.num3:
click(3);
break;
case R.id.num4:
click(4);
break;
case R.id.num5:
click(5);
break;
}
}
public void click(int clicked) {
textViews[clicked].setText("Clicked");
}
OPTION 2: (Note to shorten your time - the change is in the last function).
public static final int L = 6;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Random rand = new Random();
int[] digits = {rand.nextInt(10), rand.nextInt(10), rand.nextInt(10), rand.nextInt(10), rand.nextInt(10), rand.nextInt(10)};
for (int i = 0; i < L; i++) {
textViews[i] = (TextView) findViewById(getResources().getIdentifier("num" + String.valueOf(i), "id", getPackageName()));
textViews[i].setOnClickListener(this);
textViews[i].setText(String.valueOf(digits[i]));
}
}
#Override
public void onClick(View view) {
int id = view.getId();
switch (id) {
case R.id.num0:
click(0);
break;
case R.id.num1:
click(1);
break;
case R.id.num2:
click(2);
break;
case R.id.num3:
click(3);
break;
case R.id.num4:
click(4);
break;
case R.id.num5:
click(5);
break;
}
}
public void click(int clicked) {
((TextView) findViewById(getResources().getIdentifier("num" + String.valueOf(clicked),"id",getPackageName())).setText("Clicked");
}
Take into consideration I have more than a TextView array, and in some function I have to get 5 views again, will it be better to declare them as global variables? I read somewhere most of the time using global variables is not good and it is against the whole idea of functions, but it seems more simple here.. Sorry about my English and thank you all.
First off, you do not need to worry about performance issues if the textViews object is declared globally. It is minuscule.
Now in your code,if the only reason to declare textViews array object is to reference it in click() method, then there is no need of declaring it globally.
Instead, you can pass the view object provided by the overridden onClick() method to your click() method.
#Override
public void onClick(View view) {
int id = view.getId();
switch (id) {
case R.id.num0:
click(view);
break;
case R.id.num1:
click(view);
break;
case R.id.num2:
click(view);
break;
case R.id.num3:
click(view);
break;
case R.id.num4:
click(view);
break;
case R.id.num5:
click(view);
break;
}
}
public void click(View viewClicked) {
((TextView))viewClicked.setText("Clicked")
}
I am working on an app and trying to update Button background color using on click. What I want to do is,
1) Wait for 0.5 seconds to check answer is right or not. If answer is right, change button color to Green else change it to Red.
2) After button's color change wait for another .5 seconds and than call a function to update question.
Here is my onClick method,
#Override
public void onClick(View v) {
if(totalQuestionsAsked <= 10){
if(score >= 10)
score = 10;
//Setting up button and image
final Button btnOne = (Button)findViewById(R.id.btn_one);
final Button btnTwo = (Button)findViewById(R.id.btn_two);
final Button btnThree = (Button)findViewById(R.id.btn_three);
final Button btnFour = (Button)findViewById(R.id.btn_four);
final ImageView flagImg = (ImageView)findViewById(R.id.flag_img);
final JSONArray country = getFilesArray()[0];
final JSONArray flag = getFilesArray()[1];
final View view = v;
switch (v.getId()){
case R.id.btn_one:
btnOne.setBackgroundColor(Color.parseColor("#00b0ff"));
break;
case R.id.btn_two:
btnTwo.setBackgroundColor(Color.parseColor("#00b0ff"));
break;
case R.id.btn_three:
btnThree.setBackgroundColor(Color.parseColor("#00b0ff"));
break;
case R.id.btn_four:
btnFour.setBackgroundColor(Color.parseColor("#00b0ff"));
break;
}
final Handler handler = new Handler();
final Runnable runnerTwo = new Runnable() {
#Override
public void run() {
if(totalQuestionsAsked <= 10){
createCountryElements(flag, country, btnOne, btnTwo, btnThree, btnFour, flagImg);
}else{
Toast.makeText(MainActivity.this, "Your total score is: " + String.valueOf(score),
Toast.LENGTH_LONG).show();
}
}
};
Runnable runnerOne = new Runnable() {
#Override
public void run() {
if(view.getTag().equals(flagImg.getTag())){
score++;
switch (view.getId()){
case R.id.btn_one:
setButtonGreen(R.id.btn_one);
break;
case R.id.btn_two:
setButtonGreen(R.id.btn_two);
break;
case R.id.btn_three:
setButtonGreen(R.id.btn_three);
break;
case R.id.btn_four:
setButtonGreen(R.id.btn_four);
break;
}
}else{
switch (view.getId()){
case R.id.btn_one:
setButtonRed(R.id.btn_one);
break;
case R.id.btn_two:
setButtonRed(R.id.btn_two);
break;
case R.id.btn_three:
setButtonRed(R.id.btn_three);
break;
case R.id.btn_four:
setButtonRed(R.id.btn_four);
break;
}
}
totalQuestionsAsked++;
handler.postDelayed(runnerTwo, 1000);
}
};
handler.postDelayed(runnerOne, 500);
}
}
So it is just not changing button's background color. Everything else is working properly. Can anyone tell me where is my mistake?
Thank you for helping me. :D
btnOne.setBackgroundColor(#00b0ff);
will do the trick ;)
I found the mistake, it is not working because I am not changing it to Green. So it is working just not changing to different color. Thank you all for helping me. :D
In this application i am displaying 6 images randomly from an array containing drawables(named vmarray[12] ) and after 1 minute(using runnable postdelayed) switching is performed to another layout containing a single button with id BUTTON1 and setting the button background to one of the image from the earlier displayed images. I am using LAYOUTINFLATER for switching between layouts
On that button (Button1) onclick i want to do some work, but the PROBLEM IS when i implement onclicklistener and onclick method, the app crashes.
IF i remove the implements onclicklistener everything runs fine. The BUTTON1 is located perfectely through findviewbyid and its background correctly sets to an image. BUT Implementing onclicklister is crashing the app.
here is the code..
int[] vmarray= {R.drawable.vm1bulb, R.drawable.vm2chair, R.drawable.vm3comb,
R.drawable.vm4cycle,R.drawable.vm5dairy,R.drawable.vm6fan,R.drawable.vm7mobile,
R.drawable.vm8pen,R.drawable.vm9shoes,R.drawable.vm10toothbrush,
R.drawable.vm11bangle, R.drawable.vm12watch};
#Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
inflater = (LayoutInflater) getSystemService(LAYOUT_INFLATER_SERVICE);
setContentView(R.layout.cacrvisualmem);
firstview =(LinearLayout)this.findViewById(R.id.firsthumlayout);
secondview = (LinearLayout) inflater.inflate(R.layout.cacrvisualmempart1, null);
for(int i=0;i<6;i++)
{
final int a = i;
button_var[a] = (Button)findViewById(idArray[a]);
}
// IN FIRST LAYOUT, THERE ARE 6 BUTTONS AND THEIR BACKGROUND IS RANDOMLY SET
// DRAWABLES FROM ARRAY "vmarray". the following code is for that
Random randomGenerator = new Random();
Random rand6 = new Random();
while (numbers.size() < 6) {
random1 = randomGenerator.nextInt(12);
random2 = rand6.nextInt(6);
if (!numbers.contains(random1) && (!numbers2.contains(random2)))
{
numbers.add(random1);
numbers2.add(random2);
b[random2].setBackgroundResource(vmarray[random1]);
count++;
}//if ends
}//while ends
Handler changeview = new Handler();
Runnable r1 = new Runnable(){
#Override
public void run() {
// TODO Auto-generated method stub
// NOW, here, after 1 minute, second view will be inflated and button1
// background is set to one the image from the array
setContentView(secondview);
b11=(Button)findViewById(R.id.button1);
queryrandvar=queryrand.nextInt(12);
switch(queryrandvar)
{
case 0:
b11.setBackgroundResource(vmarray[0]);
queryval=0;
break;
case 1:
b11.setBackgroundResource(vmarray[1]);
queryval=1;
break;
case 2:
b11.setBackgroundResource(vmarray[2]);
queryval=2;
break;
case 3:
b11.setBackgroundResource(vmarray[3]);
queryval=3;
break;
case 4:
b11.setBackgroundResource(vmarray[4]);
queryval=4;
break;
case 5:
b11.setBackgroundResource(vmarray[5]);
queryval= 5;
break;
case 6:
b11.setBackgroundResource(vmarray[6]);
queryval= 6;
break;
case 7:
b11.setBackgroundResource(vmarray[7]);
queryval= 7;
break;
case 8:
b11.setBackgroundResource(vmarray[8]);
queryval= 8;
break;
case 9:
b11.setBackgroundResource(vmarray[9]);
queryval= 9;
break;
case 10:
b11.setBackgroundResource(vmarray[10]);
queryval= 10;
break;
case 11:
b11.setBackgroundResource(vmarray[11]);
queryval= 11;
break;
}//switch ends
}//run ends
};//runnable ends
b11.setOnClickListener(null);
changeview.postDelayed(r1,10000);
} //on create method ends here
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
switch(v.getId())
{
case R.id.button1:
{
b11.setBackgroundResource(vmarray[1]);
break;
}
}//switch ends
}//onclick ends
i got it.inside runnable after switch case i have put the following and button onclick is working.RUNING FINE WITH NO APP CRASH
b11.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
b11.setBackgroundResource(vmarray[0]); //SOME RANDOM IMAGE FOR CHECKING
}
});
I have 10 buttons set up which are the answers to ten questions. When a certain button is clicked, I have a switch statement set up in my onClick method shown below. My question is what is the best way to set up the OnClickListeners for all the buttons seeing that I need to pass 2 arrays to the onClick method in order to tell if it is correct or not? Also, I need to return and integer value. Thanks
public void onClick(View v, int[] qaarray, int questionorder) {
int x=0;
switch(v.getId())
{
case R.id.imageButton0:
if(qaarray[0] == questionorder){
//correct
}else{
//incorrect
}
break;
case R.id.imageButton1:
if(qaarray[1] == questionorder){
// correct
}else{
//incorrect
}
break;
case R.id.imageButton2:
if(qaarray[2] == questionorder){
// correct
}else{
//incorrect
}
break;
case R.id.imageButton3:
if(qaarray[3] == questionorder){
// correct
}else{
//incorrect
}
break;
case R.id.imageButton4:
if(qaarray[4] == questionorder){
//correct
}else{
//incorrect
}
break;
case R.id.imageButton5:
if(qaarray[5] == questionorder){
//correct
}else{
//incorrect
}
break;
case R.id.imageButton6:
if(qaarray[6] == questionorder){
//correct
}else{
//incorrect
}
break;
case R.id.imageButton7:
if(qaarray[7] == questionorder){
//correct
}else{
//incorrect
}
break;
case R.id.imageButton8:
if(qaarray[8] == questionorder){
//correct
}else{
//incorrect
}
break;
case R.id.imageButton9:
if(qaarray[9] == questionorder){
//correct
}else{
//incorrect
}
break;
default:
throw new RuntimeException("Unknown button ID");
}
}
The OnClickListener only gives you one parameter, which is the View:
void onClick(View v);
But you don't have to pass the questions and 'order' to the method to have what you want. One of the technique you can use is the setTag() method of View:
int[] button = new int[] { R.id.imageButton1, R.id.imageButton2.... };
private class AnswerPair{
public int questionOrder;
public int answer;
}
public void onCreate(Bundle bundle){
for(int i=0; i<NO_OF_BUTTON; i++){
AnswerPair ans = new AnswerPair();
ans.questionOrder = i;
ans.answer = 0; // SET this
getViewById(button[i]).setTag(ans);
getViewById(button[i]).setOnClickListener(this);
}
}
public void onClick(View v){
if (v.getTag() == null) return;
try{
AnswerPair answer = (ans)v.getTag();
// Check answer == question order? index?
}catch(exception e) return;
}
You can implement as many OnClickListeners as you want and assign different listeners for each button.
public void onCreate(Bundle bundle){
setContentView(R.layout.main);
Button b = (Button) findViewById(R.id.myButton)
b.setOnClickListener(new MyListener());
}
private class MyListener implements OnClickListener {
#Override
public void onClick(View v) {
// Your code here
}
}
i think a lot of people know this already, but there's a shortcut you can use instead of having different instances of onClickListeners and assigning them in code using setOnClickListener(x).
In your button XML, give it the android:onClick property, and assign it a string you like, for example,
android:onClick="clickOne"
In the activity the sets this xml as its content view, create a method named clickOne with a View parameter.
public void clickOne(View view)
Whatever you place on this method will be executed when you click the button.