my question is how can I make a set of clickable images on Android.
I can make one clickable sphere by using ShapeDrawable, however I want to make more than one at once and still be able to get clicks in all of them.
Moreover I want to position them on screen at my will, instead of auto positioned as with layouts.
The number of spheres can change as can the places.
This is the code I use to make one:
Main.java
package com.teste;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.LinearLayout;
import android.widget.Toast;
public class Main extends Activity {
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
LinearLayout layout = new LinearLayout(this);
CustomDrawableView mCustomDrawableView = new CustomDrawableView(this, 100, 100, 50, 50, 0xff74AC23);
CustomDrawableView mCustomDrawableView2 = new CustomDrawableView(this, 10, 10, 50, 50, 0xffffffff);
mCustomDrawableView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Toast.makeText(getBaseContext(), "Clicked green ball", Toast.LENGTH_SHORT).show();
}
});
mCustomDrawableView2.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Toast.makeText(getBaseContext(), "Clicked white ball", Toast.LENGTH_SHORT).show();
}
});
layout.addView(mCustomDrawableView);
layout.addView(mCustomDrawableView2);
setContentView(layout);
}
}
CustomDrawableView.java
package com.teste;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.drawable.ShapeDrawable;
import android.graphics.drawable.shapes.OvalShape;
import android.view.View;
import android.view.ViewGroup.LayoutParams;
public class CustomDrawableView extends View {
private ShapeDrawable mDrawable;
public CustomDrawableView(Context context, int i, int j, int k, int l, int m) {
super(context);
LayoutParams params = new LayoutParams(LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT);
super.setLayoutParams(params);
mDrawable = new ShapeDrawable(new OvalShape());
mDrawable.getPaint().setColor(m);
mDrawable.setBounds(i, j, i + k, j + l);
}
protected void onDraw(Canvas canvas) {
mDrawable.draw(canvas);
}
}
Hope you can help :)
It should be as easy as making your clas
CustomDrawableView extends View implements OnClickListener {
// all your code here
public void onClick(View v) {
// your callback function here
}
}
Take a look at one example I wrote some time ago in this answer: Android onClick method doesn't work on a custom view
Related
Sorry for my bad English I'm a beginner of android and now I'm stuck.
Now my Question is how can I set the random colors to the background with the OnClickListener. Can you maybe help my with this problem?
I have one class (Kleurenpalet.java)
package com.example.pstek.randomcolor;
import android.graphics.Color;
import java.util.Random;
public class Kleurenpalet{
private static String[] kleur = {
"#39add1", // light blue
"#3079ab", // dark blue
"#3FD52D", // green
"FFFF0000", // red
""};
public int getRandomColor() {
Random rand = new Random();
int color = rand.nextInt(kleur.length);
return Color.parseColor(kleur[color]);
}
}
And I have my main class :
package com.example.pstek.tegeltjeswijsheid;
import android.support.constraint.ConstraintLayout;
import android.support.constraint.solver.widgets.ConstraintWidget;
import android.support.v4.content.ContextCompat;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.text.Layout;
import android.view.View;
import android.widget.Button;
import android.widget.TextView;
import java.util.Random;
public class MainActivity extends AppCompatActivity {
private ConstraintLayout layout;
private Button randombutton;
int randomColor = new Kleurenpalet().getRandomColor();
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
layout = findViewById(R.id.layout);
randombutton = findViewById(R.id.button);
randombutton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
layout.setBackgroundColor(ContextCompat.getColor(getApplicationContext(), ;
}
});
}
}
in the MainActivity code this :
public class MainActivity extends AppCompatActivity {
private ConstraintLayout layout;
private Button randombutton;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
layout = findViewById(R.id.layout);
randombutton = findViewById(R.id.button);
randombutton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
int randomColor = new Kleurenpalet().getRandomColor();
layout.setBackgroundColor(randomColor);
}
});
}
}
Perhaps call setBackgroundColor with the initialized color:
layout.setBackgroundColor(randomColor);
Or a different one each time:
layout.setBackgroundColor(new Kleurenpalet().getRandomColor());
I do not understand what you try to do here:
layout.setBackgroundColor(ContextCompat.getColor(getApplicationContext(), ;
Why did you leave empty space there? Moreover, if you parse color in your Kleurenpalet, you must use without ContextCompat. Just set your color like this:
layout.setBackgroundColor(randomColor);
ContextCompat is for parsing color from resources file, for instance:
layout.setBackgroundColor(
ContextCompat.getColor(
getApplicationContext(),
R.color.colorPrimary
)
);
You must put "Random Num" and "layout set Color" in button click event :
randombutton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
int randomColor = new Kleurenpalet().getRandomColor();
layout.setBackgroundColor(randomColor);
}
});
I have a imageview that randomly generate 1 out of 2 possibles images clicking on one button.
I want that when one image is showed (R.drawable.aa) and I press other button, a toast is shown.
My problem is that once a random image is shown and click on the other button, nothing happens.
package com.example.isaiasalarcon.menu;
import java.util.Random;
import java.util.jar.Attributes;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.Toast;
import static com.example.isaiasalarcon.menu.R.drawable.aa;
public class buho extends Activity {
// UI components
private Button drawButton;
private Button boton2;
private ImageView cardImage;
// Random object
private final static Random random = new Random();
// The card deck
private final static int[] cardDeck = new int[] {
R.drawable.aa,
R.drawable.a2,
};
private Integer q;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_buho);
drawButton = (Button)findViewById(R.id.drawButton);
boton2 = (Button)findViewById(R.id.button2);
cardImage = (ImageView)findViewById(R.id.cardImage);
drawButton.setOnClickListener(new View.OnClickListener() {
public void onClick(View arg0)
{
Integer q = cardDeck[random.nextInt(cardDeck.length)];
cardImage.setImageResource(q);
}
});
boton2.setOnClickListener(new View.OnClickListener() {
public void onClick(View arg0) {
if (q.equals(R.drawable.aa)) {
Toast toast = Toast.makeText(buho.this, "si", Toast.LENGTH_LONG);
toast.show();
} else {
Toast toast = Toast.makeText(buho.this, "no", Toast.LENGTH_LONG);
toast.show();
}
}
});
}
}
two things:
1) Integer q I don't see a reason why this needs to be an Integer. You should be able to int
2) your q inside the onClick is creating a NEW variable called q. You need to update your code to the following: (note how it doesn't have the Type declaration before it, so it means to use the previously declared variable)
drawButton.setOnClickListener(new View.OnClickListener() {
public void onClick(View arg0)
{
q = cardDeck[random.nextInt(cardDeck.length)];
cardImage.setImageResource(q);
}
});
i am working on android app
in which i have an animated image.
my code is
Display display = getWindowManager().getDefaultDisplay();
int width = display.getWidth()/2;
left = new TranslateAnimation(0, hight, width, hight);
left1= new TranslateAnimation( 480, 10, 0, 10);
left.setDuration(2000);
left.setAnimationListener(this);
b1 =(ImageView)findViewById( R.id.balloon);
b1.setOnClickListener(this);
b1.startAnimation(left);
#Override
public void onClick(View v) {
Toast.makeText(this, "Clicked", 27).show();
}
using this code i am able to animate ballon or my picture but i the onclick lisnter only works when animation is completed i want onclicklistner should work during animation how to do this.
sorry for bad english
Override onAnimationStart and onAnimationEnd functions in your AnimationListener. Keep a variable to check whether animation is playing when the image clicked.
import android.os.Bundle;
import android.app.Activity;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.animation.Animation;
import android.view.animation.Animation.AnimationListener;
import android.view.animation.TranslateAnimation;
import android.widget.ImageView;
import android.widget.Toast;
public class MainActivity extends Activity {
private ImageView imageView;
private boolean animationPlaying;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
TranslateAnimation animation = new TranslateAnimation( 480, 10, 0, 10);
animation.setDuration(2000);
animation.setAnimationListener(new AnimationListener() {
#Override
public void onAnimationStart(Animation animation) {
animationPlaying = true;
}
#Override
public void onAnimationRepeat(Animation animation) {
}
#Override
public void onAnimationEnd(Animation animation) {
animationPlaying = false;
}
});
imageView = (ImageView) findViewById(R.id.imageView1);
imageView.startAnimation(animation);
imageView.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
if(animationPlaying) {
Toast.makeText(getBaseContext(), "Click", Toast.LENGTH_SHORT).show();
} else {
Log.d("ANIMATION", "click missed because animation was not playing");
}
}
});
}
}
Where in this code would I put a thread delay, that will happen after the completion of onCreate(), which means also after the completion/showing of onDraw()? Afterwards I will be calling grid.clearPattern() which clears the pattern drawn on the canvas when grid.displayPattern() was called. So afterwards I will still need to be able to modify the canvas.
package com.patterns;
import android.app.Activity;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.os.Bundle;
import android.os.Handler;
import android.util.Log;
import android.view.MotionEvent;
import android.view.View;
public class PlayGame extends Activity implements View.OnTouchListener {
int size;
Grid grid;
PatternView patternview;
/** Called when the activity is first created. */
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
size = getIntent().getExtras().getInt("size");
patternview = new PatternView(this);
setContentView(patternview);
Handler pauser = new Handler();
pauser.postDelayed(new Runnable() {
public void run() {
patternview.clearDraw();
}
}, 2000);
patternview.setOnTouchListener(this);
}
public class PatternView extends View {
Paint paint = new Paint();
public PatternView(Context context){
super(context);
}
protected void clearDraw() {
Log.d("debug", "clearDraw called");
grid.clearPattern();
}
#Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
grid = new Grid(size, size, getWidth(), getWidth(), canvas, paint);
grid.createPattern();
grid.displayPattern();
Log.d("debug", "lines drawn");
grid.setBoard();
Log.d("debug", "board set");
}
}
#Override
public boolean onTouch(View arg0, MotionEvent arg1) {
//Log.d("debug", "screen touched");
grid.screenTouch(arg1);
grid.fillActiveRectangles();
return false;
}
}
Maybe stick the call to grid.clearPattern() into an android.os.Handler? Had a similar app-pausing problem and this did the trick for me. So stick something like this at the end of onCreate() -- the 3500 is a pause in milliseconds, choose the value that you want.
Handler pauser = new Handler();
pauser.postDelayed (new Runnable() {
public void run() {
grid.clearPattern();
}
}, 3500);
Could it be like this?
grid.createPattern();
grid.displayPattern(canvas, paint);
Thread.sleep(2000);
But it will be a pain...
Question is about android development, more exactly it is about buttons and cumstom views.
I'm using four buttons in Linear Layouts and one custom view in which I draw images.
When I use method to do this (I override onDraw() ) everything works just fine, except my buttons react quite slow on pressing them. Just removing the onDraw functions leaves them working quickly.
So, my questions are:
Why do those buttons work that slow? I just cant find out why!
Do I have to use self created buttons in the custom view?
And how to solve this?
Thsi is the class I use the onDraw Method:
import android.content.Context;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.text.TextUtils;
import android.util.AttributeSet;
import android.widget.ImageView;
public class test extends ImageView{
Context mContext;
String[] medium;
final int pspawn[]={64,32};
public test(Context context, AttributeSet attrs) {
super(context, attrs);
mContext = context;
}
private String getMapInfo(Integer counter){
String[] mapArray = TextUtils.split(map, " ");
return mapArray[counter];
}
public void onDraw(Canvas canvas){
int x = 0;
int y = 0;
for(int i = 0; i<100; i = i+1)
{
String mapinfo = getMapInfo(i);
if (mapinfo.equals("x"))
{
canvas.drawBitmap(BitmapFactory.decodeResource(mContext.getResources(),R.drawable.t1), x, y, null);
}
x = x + 32;
if (x == 320)
{
y = y + 32;
x = 0;
}
canvas.drawBitmap(BitmapFactory.decodeResource(mContext.getResources(),R.drawable.t3), pspawn[0], pspawn[1],null);
invalidate();
}
}
}
And this is my main class:
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.Toast;
public class desimain extends Activity{
private Thread worker;
private Runnable newMsg;
private OnClickListener getKeystroke;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
getKeystroke = new OnClickListener(){
public void onClick(View view) {
switch(view.getId()){
case R.id.Up:
worker = new Thread(newMsg);
worker.start();
break;
case R.id.Down:
Toast.makeText(getApplicationContext(), "Down", Toast.LENGTH_SHORT).show();
break;
case R.id.Left:
Toast.makeText(getApplicationContext(), "Left", Toast.LENGTH_SHORT).show();
break;
case R.id.Right:
Toast.makeText(getApplicationContext(), "Right", Toast.LENGTH_SHORT).show();
break;
}
};
};
Button pressUp = (Button) findViewById (R.id.Up);
pressUp.setOnClickListener(getKeystroke);
Button pressDown = (Button) findViewById (R.id.Down);
pressDown.setOnClickListener(getKeystroke);
Button pressLeft = (Button) findViewById (R.id.Left);
pressLeft.setOnClickListener(getKeystroke);
Button pressRight = (Button) findViewById (R.id.Right);
pressRight.setOnClickListener(getKeystroke);
newMsg = new Runnable(){
public void run() {
runOnUiThread(new Runnable() {
public void run() {
Toast.makeText(getApplicationContext(), "Up", Toast.LENGTH_SHORT).show();
}
});
}
};
}
}
PS: I know this code isnt very beautiful, but at the moment i just try to figure out the basics I need...
Your buttons do not respond because you are taking up much too much time on the main application thread in your onDraw() method. Please cache your bitmaps rather than loading files from flash 200 times per draw.