I have a button that moves around the screen and changes image and every 5th time it's pressed I want it to also do an additional function (print a command). I can't figure out how to only trigger an event every 5th button press though? I have tried counting with an int but I am getting errors about then referring to the int in the nested if condition. I had tried playing around with the final prefix but can't figure out how to get it working so that I may edit the variable both outside and inside the if condition.
Error:(58, 20) error: local variable i is accessed from within inner class; needs to be declared final
public void addListenerOnButton() {
int i=0;
imageButton = (ImageButton) findViewById(R.id.imageButton1);
imageButton.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View arg0) {
;
//Move position
Random r = new Random();
int buttonHeight;
int buttonWidth;
int xPos = r.nextInt(480);
int yPos = r.nextInt(800);
imageButton.setX(xPos);
imageButton.setY(yPos);
//Change image
int[] imageIds = {
R.drawable.pic1,
R.drawable.pic2,
R.drawable.pic3,
R.drawable.pic4,
R.drawable.pic5,
R.drawable.pic6,
R.drawable.pic7,
R.drawable.pic8,
R.drawable.pic9,
R.drawable.pic10
};
int randomImageId = imageIds[r.nextInt(imageIds.length)];
imageButton.setImageResource(randomImageId);
if(i==5){
Toast offMsg = Toast.makeText(getBaseContext(),
"This is the fifth button press", Toast.LENGTH_SHORT);
offMsg.show();
int i=0;
}
}
});
}
}
Declare your counter variable inside the OnClickListener:
imageButton.setOnClickListener(new OnClickListener() {
int i = 0;
#Override
public void onClick(View arg0) {
...
if(++i == 5){
Toast offMsg = Toast.makeText(getBaseContext(),
"This is the fifth button press", Toast.LENGTH_SHORT);
offMsg.show();
i=0;
}
}
});
You get that error because you can't access local variables from an inner class.
Declare your variable 'i' as an instance variable i.e. define it outside addListenerOnButton() method and remove the int i = 0 declaration from addListenerOnButton() method and also change the int i = 0 line after offMsg.show() to i = 0.
You also need to increment the variable 'i' every time the image is clicked.
Related
I have a problem with my simple android app. When I launch it, the questions seems to be a step ahead of the answers I enter as input. For example If the question was to be 3x3 = ?, It will only accept the correct answer for the next question. So any answer I give in the current question will always be wrong. I tested this by continuously entering the same same answer.
Any pointers would be much appreciated. I hope this make sense!
public class MainActivity extends AppCompatActivity {
int value3;
int answer;
EditText answer_field;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
final ImageView leftNumber = findViewById(R.id.left_number);
final ImageView rightNumber = findViewById(R.id.right_number);
Button myButton = findViewById(R.id.answer_button);
final int[] numberArray = new int[]{
R.drawable.number_0,
R.drawable.number1,
R.drawable.number2,
R.drawable.number3,
R.drawable.number4,
R.drawable.number5,
R.drawable.number6,
R.drawable.number7,
R.drawable.number8,
R.drawable.number9,
};
leftNumber.setImageResource(numberArray[0]);
rightNumber.setImageResource(numberArray[0]);
myButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// Create a random number generator
Random randomNumberGenerator = new Random();
int value1 = randomNumberGenerator.nextInt(10);
leftNumber.setImageResource(numberArray[value1]);
// Create a new random number
int value2 = randomNumberGenerator.nextInt(10);
// Set the right dice image using an image from the diceArray.
rightNumber.setImageResource(numberArray[value2]);
answer_field = findViewById(R.id.answer_field);
answer = valueOf(answer_field.getText().toString());
value3 = value1 * value2;
if(value3 == answer) {
showToast("Correct");
}
}
});
}
public void showToast(String text){
Toast.makeText(MainActivity.this, text, Toast.LENGTH_LONG).show();
}
}
Thank you!
You are generating the values at the onClick of your answer button wich means that the values to multiply will be set (or reset) randomly every time the user hit the answer button; put the logic to generate the values outside the onclick, so when the user clicks on it only the comparison will be made, somewhat like this:
[...]
leftNumber.setImageResource(numberArray[0]);
rightNumber.setImageResource(numberArray[0]);
// Create a random number generator
Random randomNumberGenerator = new Random();
int value1 = randomNumberGenerator.nextInt(10);
leftNumber.setImageResource(numberArray[value1]);
// Create a new random number
int value2 = randomNumberGenerator.nextInt(10);
// Set the right dice image using an image from the diceArray.
rightNumber.setImageResource(numberArray[value2]);
answer_field = findViewById(R.id.answer_field);
myButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
answer = valueOf(answer_field.getText().toString());
value3 = value1 * value2;
if(value3 == answer) {
showToast("Correct");
}
}
});
[...]
I have an array of bitmaps ArrayList<Bitmap> images = new ArrayList<>(3) and need to change the image of a ImageButton in every click, first images(0) then, after I click image(1) and finally image(2).
For this I am using myImageButton.setImageBitmap(images.get(0)) for the first image, how do I change to the next and then to the third?
You should use
int currentPos = 0;
onclick(){
currentPos = (currentPos+1)%(images.size()-1)
myImageButton.setImageBitmap(images.get(currentPos))
}
You can use
int currentPos = 0;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
...
myImageButton.setImageBitmap(images.get(0))
}
#Override
public void onClick(View v){
currentPos++;
if(currentPos == 2){
// if the imagebutton has the bitmap from position 2, you can do what you want
//example:
currentPos = 0;// so you have the first Bitmap you had when the user didn't click on the ImageButton
}
myImageButton.setImageBitmap(images.get(currentPos));
}
I'm looking to call a few buttons but seem to be getting a NULL when trying to findbyviewid. When I activate this activity, it crashes.
//CREATE INSTANCE OF GLOBAL - QUESTIONS/ANSWERS
Global global = Global.getInstance();
//CURRENT QUESTION
static int QQ = 0;
//CORRECT ANSWER COUNT
static int correctAnswers = 0;
//CREATE VARIABLE FOR TEXTVIEW/QUESTION
TextView textQuestion = (TextView) findViewById(R.id.textQuestion);
//CREATE VARIABLES FOR BUTTONS/ANSWERS
Button buttonOne = (Button) findViewById(R.id.answerOne);
Button buttonTwo = (Button) findViewById(R.id.answerTwo);
Button buttonThree = (Button) findViewById(R.id.answerThree);
Button buttonFour = (Button) findViewById(R.id.answerFour);
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_practice_questions);
setButtons();
buttonOne.setOnClickListener(this);
buttonTwo.setOnClickListener(this);
buttonThree.setOnClickListener(this);
buttonFour.setOnClickListener(this);
}
public void setButtons()
{
//SET QUESTION STRING TO TEXTVIEW
textQuestion.setText(global.getQ(QQ));
//SET ANSWER STRINGS TO BUTTONS' TEXT
buttonOne.setText(global.getA(QQ, 0));
buttonTwo.setText(global.getA(QQ, 1));
buttonThree.setText(global.getA(QQ, 2));
buttonFour.setText(global.getA(QQ, 3));
}
#Override
public void onClick(View v)
{
switch(v.getId())
{
case R.id.answerOne:
checkAnswer(0, buttonOne);
break;
case R.id.answerTwo:
checkAnswer(1, buttonTwo);
break;
case R.id.answerThree:
checkAnswer(2, buttonThree);
break;
case R.id.answerFour:
checkAnswer(3, buttonFour);
break;
default:
break;
}
}
public void checkAnswer(int a, Button b){
//IF AN INCORRECT ANSWER WAS CHOSEN, MAKE THE BACKGROUND RED
if(!global.getS(QQ, a))
{
b.setBackgroundColor(Color.RED);
}
else
{
//INCREMENT THE CORRECT ANSWER COUNTER
correctAnswers++;
}
//SET BACKGROUND OF CORRECT BUTTON TO GREEN
if(global.getS(QQ, 0))
{
buttonOne.setBackgroundColor(Color.GREEN);
}
else if(global.getS(QQ, 1))
{
buttonTwo.setBackgroundColor(Color.GREEN);
}
else if(global.getS(QQ, 2))
{
buttonThree.setBackgroundColor(Color.GREEN);
}
else if(global.getS(QQ, 3))
{
buttonFour.setBackgroundColor(Color.GREEN);
}
else
{
//IF NO ANSWER IS CORRECT, SET ALL TO BLUE
buttonOne.setBackgroundColor(Color.BLUE);
buttonTwo.setBackgroundColor(Color.BLUE);
buttonThree.setBackgroundColor(Color.BLUE);
buttonFour.setBackgroundColor(Color.BLUE);
}
//MOVE TO NEXT QUESTION
}
I have 4 buttons in the XML file and want to be able to set the text to them, as well as run a listener for the set of buttons (answers to a question). When one of the buttons is clicked, it should determine if it's the correct answer by pulling the status (true/false) and highlighting it red if it's incorrect. It then highlights the correct answer green.
At least, some of this is in theory and I'm trying to test it out, but I can't start the activity without crashing.
I'm not 100% sure but I think you can't do the findViewById at the instance constructions. You need to those inside onCreate() (after you called setContentView)
Just how i said in comment, you should initialize it in OnCreate method, cause you set view layout for activity here. And before you do it, all findViewById returns null.
So, here your code:
Button buttonOne;
Button buttonTwo;
Button buttonThree;
Button buttonFour;
TextView textQuestion;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_practice_questions);
buttonOne = (Button) findViewById(R.id.answerOne);
buttonTwo = (Button) findViewById(R.id.answerTwo);
buttonThree = (Button) findViewById(R.id.answerThree);
buttonFour = (Button) findViewById(R.id.answerFour);
textQuestion = (TextView) findViewById(R.id.textQuestion);
[...]
}
I am new to android and I need help.
I want my image which is falling from the top of screen to get invisible when I click a button on the keyboard which has the same tag as the image. Although I have implemented the above points a problem arises when I want to show the next animation again immediately after the previous image gets invisible. This is my code for animation.
public void startAnimation(final ImageView aniView)
{
animator= ValueAnimator.ofFloat(0 ,.85f);
animator.setDuration(Constants.ANIM_DURATION);
animator.setInterpolator(null);
//generation of random values
Random rand = new Random();
index = rand.nextInt((int) metrics.widthPixels);
//for debugging
i = Integer.toString(index);
Log.e(" index is :", i);
animator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener()
{
#Override
public void onAnimationUpdate(ValueAnimator animation)
{
float value = ((Float) (animation.getAnimatedValue())).floatValue();
aniView.setTranslationX(index);
aniView.setTranslationY((height+ (50*mScale))*value);
//aniView.setTranslationY(height);
}
});
animator.start();
}
//keyboard methods goes here
#Override
public void onClick(View v)
{
gettext(v);
}
private void gettext(View v)
{
try
{
String b = "";
b = (String) v.getTag();
String img_val = map.get(b);
int imgid = (Integer) imageView.getTag();
Log.e("img values=:", img_val+" "+imgid);
if(img_val.equals(ALPHABETS[imgid]))
{
imageView.setVisibility(View.INVISIBLE);
animator.start();
//trying to start the animation again
}
I am using the animation.addupdateListener to call the animation again and again but it only calls when the .ofFloat finishes on the value. When I click on the appropriate button the animation gets invisible but the next animation starts again after the same time. I want to start it immediately.
Basically calling start() again won't work. you need to "reset" the animation somehow, did you try calling end() before ?
animator.end();
animator.start();
Can anyone help me work out where I'm going wrong here. On the button click the media player plays one of the mfiles at random and I'm trying to set a textview depending on which file was played. Currently the setText if statements only match the audio playing half the time. Really not sure where I'm going wrong here.
private final int SOUND_CLIPS = 3;
private int mfile[] = new int[SOUND_CLIPS];
private Random rnd = new Random();
MediaPlayer mpButtonOne;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mfile[0] = R.raw.one;
mfile[1] = R.raw.two;
mfile[2] = R.raw.three;
//Button setup
Button bOne = (Button) findViewById(R.id.button1);
bOne.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
final TextView textOne = (TextView)findViewById(R.id.textView1);
mpButtonOne = MediaPlayer.create(MainActivity.this, mfile[rnd.nextInt(SOUND_CLIPS)]);
if (mpButtonOne==null){
//display a Toast message here
return;
}
mpButtonOne.start();
if (mfile[rnd.nextInt(SOUND_CLIPS)] == mfile[0]){
textOne.setText("one");
}
if (mfile[rnd.nextInt(SOUND_CLIPS)] == mfile[1]){
textOne.setText("two");
}
if (mfile[rnd.nextInt(SOUND_CLIPS)] == mfile[2]){
textOne.setText("three");
}
mpButtonOne.setOnCompletionListener(new soundListener1());
{
}
So just to clarify the problem I am having is that the setText only matches the audio occasionally, not on every click. The rest of the time it displays the wrong text for the wrong audio.
You are choosing another random file
mfile[rnd.nextInt(SOUND_CLIPS)]
set that to a variable in onClick() then check against that variable in your if statement
public void onClick(View v) {
int song = mfile[rnd.nextInt(SOUND_CLIPS)];
final TextView textOne = (TextView)findViewById(R.id.textView1);
mpButtonOne = MediaPlayer.create(MainActivity.this, song);
if (song == mfile[0]){
textOne.setText("one");
}
Edit
To make it a member variable so you can use it anywhere in the class, just declare it outside of a method. Usually do this before onCreate() just so all member variables are in the same place and it makes your code more readable/manageable.
public class SomeClass extends Activity
{
int song;
public void onCreate()
{
// your code
}
then you can just initialize it in your onClick()
public void onClick(View v) {
song = mfile[rnd.nextInt(SOUND_CLIPS)];
final TextView textOne = (TextView)findViewById(R.id.textView1);
mpButtonOne = MediaPlayer.create(MainActivity.this, song);