Android: Changing ImageView size is not working - java

I am trying to change my ImageView size, but I can't seem to change both - width and height. If I just change one of them, then all works correctly, but when I try to change both, only width is changed.
I have the size in dp: width 22 and height 38, and I convert them to px. Is there another way to do so? I have tried many other ways, but they don't seem to work either.
Could someone tell me, what I should do differently?
Here is my code:
public GridLayout gridLayout;
public GridLayout.Spec row = GridLayout.spec(0);
public GridLayout.Spec col = GridLayout.spec(3);
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
gridLayout = (GridLayout) findViewById(R.id.gameGrid);
createBlock();
}
public void createBlock() {
ImageView block = new ImageView(this);
block.setImageResource(R.drawable.red);
if (gridLayout != null) {
gridLayout.addView(block, new GridLayout.LayoutParams(row, col));
int width_in_dp = 22, height_in_dp = 38;
final float scale = getResources().getDisplayMetrics().density;
int width_in_px = (int) (width_in_dp * scale + 0.5f);
int height_in_px = (int) (height_in_dp * scale + 0.5f);
ViewGroup.LayoutParams layoutParams = block.getLayoutParams();
layoutParams.width = width_in_px;
layoutParams.height = height_in_px;
block.setLayoutParams(layoutParams);
}
}

Have you tried playing with the block's scaleType? The default is fitCenter but I usually choose centerCrop or fitXY. Here's a good webpage that describes the differences.
You can set the scaleType through ImageView's setScaleType method.

Related

Android - set Dot on random position in imported image

thanks in advance!!!
Situation:
Me and a friend has to develop an app for the university. (I think this story is common?!) We had the idea for an App, where you take or import a picture and the App make one random dot/point on this picture.
So if you stand in front of a shelf in the store and dont know which of the beers/Liqours/crisps/... you should buy, take a picture and the random dot picks for you.
Problem:
We had an imageview, where to import the picture. Go to gallery or take a photo is working. But I dont know how to set a dot in this imageView/picture. At the moment i put a second imageview over it, where a random text including "•" appears. Its more like a workaround.
Code for the dot in Class MyCanvas:
int min = 5;
int max = 500;
Random r = new Random();
int i1 = r.nextInt(max - min + 1) + min;
int i2 = r.nextInt(max - min + 1) + min;
#Override
protected void onDraw(Canvas canvas) {
// TODO Auto-generated method stub
super.onDraw(canvas);
Paint pBackground = new Paint();
pBackground.setColor(Color.TRANSPARENT);
canvas.drawRect(0, 0, 512, 512, pBackground);
Paint pText = new Paint();
pText.setColor(Color.RED);
pText.setTextSize(40);
canvas.drawText("•", i1 , i2, pText);
}
onClick method:
public void click_button_magic(View view) {
View v = new MyCanvas(getApplicationContext());
Bitmap bitmap =Bitmap.createBitmap(500/*width*/, 500/*height*/, Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(bitmap);
v.draw(canvas);
ImageView iv2 = (ImageView) findViewById(R.id.imageView_point);
iv2.setImageBitmap(bitmap);
}
If i change this code to the imageview where the imported pictures get in, the picture get white after clicking on the "Magic" button.
What i want to change:
set dot (not text)
set dot in imported image
getting from image the max and min dimension within to set the dot (width, height)
I think for this tasks i made something fundamental wrong. But i dont know what... =(
So I hope you can help me (code or tips to get on the right way)
Thank you very much and i hope my english is good enough to understand my problem!
It's hard for me to understand how you did this, because I can't see all of your code. But if I would have done this project, I would use a FrameLayout, and add the Photo with:
android:layout_width="match_parent"
android:layout_height="match_parent"
And then make a small view with round background, and make the margin left margin right be random. That way you don't need to draw on the canvas and all that hassle.
meanwhile i get a solution for getting a point in the picture.
To set an image as imageview:
...
imageview.setImageBitmap(image);
bm = image;
iv = imageview;
...
bm is now the bitmap with the wanted image
iv is the imageview
Now the Clickfunction:
public void click_button_magic(View view) {
//bei jedem Klick wird das Bild neu geladen, damit bei erneutem Klicken ein neuer Punkt erscheint
iv.setImageBitmap(bm);
ImageView img = findViewById(R.id.imageView_photoImport);
img.setDrawingCacheEnabled(true);
Bitmap scaledBitmap = img.getDrawingCache();
//get Maße des IMG
int targetWidth = scaledBitmap.getWidth();
int targetHeight = scaledBitmap.getHeight();
Bitmap targetBitmap = loadBitmapFromView(iv, iv.getWidth(), iv.getHeight());//Bitmap.createBitmap(targetWidth,targetHeight,Bitmap.Config.ARGB_8888);
//get random coordinates
int min = 5;
int maxWidth = targetWidth;
int maxHeight = targetHeight;
Random r = new Random();
int randomWidth = r.nextInt(maxWidth - min + 1) + min;
int randomHeight = r.nextInt(maxHeight - min + 1) + min;
//Paint object
Paint paint = new Paint();
paint.setStyle(Paint.Style.FILL);
paint.setColor(Color.RED);
Canvas canvas = new Canvas(targetBitmap);
canvas.drawCircle(randomWidth, randomHeight,20, paint);
img.setImageBitmap(targetBitmap);
}
public static Bitmap loadBitmapFromView(View v, int width, int height) {
Bitmap b = Bitmap.createBitmap(width , height, Bitmap.Config.ARGB_8888);
Canvas c = new Canvas(b);
v.layout(0, 0, width, height);
//Get the view’s background
Drawable bgDrawable =v.getBackground();
if (bgDrawable!=null)
//has background drawable, then draw it on the canvas
bgDrawable.draw(c);
else
//does not have background drawable, then draw white background on the canvas
c.drawColor(Color.WHITE);
v.draw(c);
return b;
}
I hope it will help someone in the future...maybe not, maybe it will

Android: Moving an ImageView from updating Values in a Thread

I am trying to make the ImageView missile1 to spawn at a random y-coordinate on the right edge of the screen and then move it left across the screen until it is off the screen, and finally move it back to a random y-coordinate on the right edge of the screen to repeat the process in an infinite loop. The code I have spawns the image at a totally random x and y coordinate location whenever the activity is restarted, but it doesn't move. Can anybody see why it doesn't move and give a solution to my problem? Some example code will be appreciated.
The thread that generates x and y coordinate values:
public class Missiles extends Thread {
private int height, width, currentscore;
private ImageView missile1, missile2, missile3, missile4, missile5;
Handler updatemissile = new Handler();
int min = 100;
RelativeLayout layout;
int setx1, sety1, setx2, sety2, setx3, sety3, setx4, sety4, setx5, sety5;
private Random rand = new Random();
TextView x, y;
Missiles(int screenheight, int screenwidth, ImageView missile01, ImageView missile02, ImageView missile03,
ImageView missile04, ImageView missile05, RelativeLayout rl, TextView xtext, TextView ytext) {
missile1 = missile01;
missile2 = missile02;
missile3 = missile03;
missile4 = missile04;
missile5 = missile05;
height = screenheight;
width = screenwidth;
layout = rl;
x = xtext;
y = ytext;
}
public void updatevalue(int value) {
currentscore = value;
}
public void run() {
SetMissilePosition position = new SetMissilePosition(missile1, layout, x, y);
updatemissile.post(position);
//width is the width of the screen as height is the height of the screen
while (true) {
setx1 = width;
position.updateX(setx1);
int randomNum = rand.nextInt((height - min) + 1) + min;
sety1 = randomNum;
position.updateY(sety1);
while (setx1 > -50) {
setx1 = setx1 - 1;
position.updateX(setx1);
}
setx1 = width;
position.updateX(setx1);
}
}
}
The Runnable Class:
public class SetMissilePosition implements Runnable{
int x1,y1, updateindicator;
ImageView missile1;
RelativeLayout layout;
TextView x,y;
SetMissilePosition(ImageView missile01, RelativeLayout relativeLayout, TextView xtext, TextView ytext) {
missile1 = missile01;
layout = relativeLayout;
x = xtext;
y = ytext;
}
public void updateX( int setx1) {
x1 = setx1;
updateindicator = 1;
}
public void updateY(int sety1) {
y1 = sety1;
updateindicator = 1;
}
public void run() {
missile1.setImageResource(R.drawable.missileanim);
layout.addView(missile1);
if(updateindicator == 1) {
missile1.setX(x1);
missile1.setY(y1);
x.setText(Integer.toString(x1));
y.setText(Integer.toString(y1));
updateindicator = 0;
}
}
}
If I am being unclear in any way or you need more code such as my MainActivity, please ask. Thanks in advance!
It sounds like you're trying to update the UI thread from off of the UI thread.
If that's the route you want to go, I'd encourage you to take a look at the 'run on ui thread' operation. Essentially, when you want to update layout positions, you can just call getContext().runOnUiThread([runnable]) and that will update your position. See here for more information: https://developer.android.com/training/multiple-threads/communicate-ui.html Some things to bear in mind:
Android runs at 60fps, so you need to make sure you're updating every 16ms or so in order to match in sync with your framerate. Otherwise your speed will be off.
Instead of doing that, why not use a Translate animation: https://developer.android.com/reference/android/view/animation/TranslateAnimation.html
You can set starting and ending x and y coordinates, you can even use them as percentages of screenwidth and length, and set the animation to repeat infinitely. If repeating infinitely won't work because you want to pick new X (or Y) values each time, you can hook something up on the end of the animation to pick new values and restart.
I found the answer myself through lots of trial end error. What I did was Created an activity that extended surface view, added a bitmap to it, updated the images coordinates in a thread, and finally passed the coordinates into another thread which updated the screen 30 times a second.

Imageview on a random position [duplicate]

This question already has answers here:
How can I dynamically set the position of view in Android?
(13 answers)
Closed 6 years ago.
I want myImageView to locate itself somewhere on a random position inside the screen, without pushing textviews away. I found this code in another thread, but I can't get it to work.
myImageView = (ImageView) findViewById(R.id.myImageView);
LinearLayout game = (LinearLayout)findViewById(R.id.game);
int width = game.getWidth();
int height = game.getHeight();
random = new Random();
int x = width;
int y = height;
int imageX = random.nextInt(x-50)+50;
int imageY = random.nextInt(y-100)+100;
myImageView.setX(imageX);
myImageView.setY(imageY);
You can give margin programmatically between certain range, may be you can use device width or height for range. Check this links for setting margin dynamically on run time and get screen dimension.
I Think first get programmatically device size then set image view width & height
WindowManager wm = (WindowManager)context.getSystemService(Context.WINDOW_SERVICE);
Display display = wm.getDefaultDisplay();
Display display = getWindowManager().getDefaultDisplay();
int width = display.getWidth(); // deprecated
int height = display.getHeight(); // deprecated
hear you get width & height now set image view size
android.view.ViewGroup.LayoutParams layoutParams =myImageView.getLayoutParams();
layoutParams.width = 30;
layoutParams.height = 30;
myImageView.setLayoutParams(layoutParams);
and if you still have a problem to change it's size try to put it inside of a LinearLayout and manipulate the imageView size using the layout params:
LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(30, 30);
myImageView.setLayoutParams(layoutParams);

android button.getWidth() returns value 0

I'm dynamically creating buttons and I want to place them randomly on the screen.
In order to do that, I'm substracting the width of the button from the screen's width.
The thing is, the function button.getWidth() always return 0.
I saw in other posts that people recommended using
#Override
public void onWindowFocusChanged(boolean hasFocus) {
super.onWindowFocusChanged(hasFocus);
placeButtonsOnScreen();
}
But even when I'm using it, it doesn't work.
private void placeButtonsOnScreen() {
Random r = new Random();
LinearLayout layout = (LinearLayout) findViewById(R.id.ordered_buttons_layout);
for (int i = 0; i < NUMBER_OF_BUTTONS; i++) {
Button hiddenButton = buttonsArr[i];
// Get random horizontal margin for the button
LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(
LinearLayout.LayoutParams.WRAP_CONTENT,
LinearLayout.LayoutParams.WRAP_CONTENT);
horizontalMargin = r
.nextInt(SCREEN_WIDTH - hiddenButton.getWidth());
layoutParams.setMargins(horizontalMargin, 50, 0, 0);
// Add the button to the screen
layout.addView(hiddenButton, layoutParams);
Log.d("button width",String.valueOf(hiddenButton.getWidth()));
}
}
Any ideas how can I position the buttons on the screen minus their width? Cos right now they get cut off from intersection with the right side of the screen.
myView.getViewTreeObserver().addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
#Override
public void onGlobalLayout() {
myView.getViewTreeObserver().removeGlobalOnLayoutListener(this);
placeButtonsOnScreen();
}
});
You should use RelativeLayouts and make buttons position according to each other (Aligning of course the one closest to the right side of the screen as alignedToParentRight = true)

How to get the button's border size in Android

How can I get the border width of a stand Android button programmatically? I simply need to resize the text to fit to the gray area and need to position other objects inline with the buttons, but I cannot do that without knowing the size of the border. I need this to work in all API's 7+. The red arrows in the image below show what I am trying to get:
Here is the code I use for creating my button:
cmdView = new Button(this);
params = new RelativeLayout.LayoutParams(widthLblViewVerbs , (int) fieldHeight);
params.leftMargin = (int) (screenWidth - params.width);
params.topMargin = (int) yPos;
cmdView.setSingleLine();
cmdView.setText("View");
cmdView.setPadding(0, 0, 0, 0);
cmdView.setTextSize(TypedValue.COMPLEX_UNIT_PX, SetTextSize(cmdView.getText().toString(), params.width, params.height));
layout.addView(cmdView, params);
NB. I've had to ask this question again because someone downvoted my question last time and I am desperate for a solution. I have made absolutely no progress with my program in weeks because I have been stuck with this and another problem. If there is something unclear about my question, please let me know and I will edit it. Thank you
My initial code recommendation from the comments can be found here. The implementation done by Dan Bray is:
final Button button = new Button(this);
params = new RelativeLayout.LayoutParams(50, 50);
layout.addView(button, params);
button.post(new Runnable()
{
#Override
public void run()
{
button.buildDrawingCache();
Bitmap viewCopy = button.getDrawingCache();
boolean stillBorder = true;
PaddingLeft = 0;
PaddingTop = 0;
while (stillBorder)
{
int color = viewCopy.getPixel(PaddingLeft, button.getHeight() / 2);
if (color != Color.TRANSPARENT)
stillBorder = false;
else
PaddingLeft++;
}
stillBorder = true;
while (stillBorder)
{
int color = viewCopy.getPixel(button.getWidth() / 2, PaddingTop);
if (color != Color.TRANSPARENT)
stillBorder = false;
else
PaddingTop++;
}
}
});
Not really clear on the question - you want the margins of the underlying view and then the set the size of the button to match ? Then Have you tried
ViewGroup.MarginLayoutParams lp = (ViewGroup.MarginLayoutParams) view.getLayoutParams();
margins are accessible via
lp.leftMargin;
lp.rightMargin;
lp.topMargin;
lp.bottomMargin;
Details here:http://developer.android.com/reference/android/view/ViewGroup.MarginLayoutParams.html
This gets the width and height of the button's border:
final Button button = new Button(this);
params = new RelativeLayout.LayoutParams(50, 50);
layout.addView(button, params);
button.post(new Runnable()
{
#Override
public void run()
{
button.buildDrawingCache();
Bitmap viewCopy = button.getDrawingCache();
boolean stillBorder = true;
PaddingLeft = 0;
PaddingTop = 0;
while (stillBorder)
{
int color = viewCopy.getPixel(PaddingLeft, button.getHeight() / 2);
if (color != Color.TRANSPARENT)
stillBorder = false;
else
PaddingLeft++;
}
stillBorder = true;
while (stillBorder)
{
int color = viewCopy.getPixel(button.getWidth() / 2, PaddingTop);
if (color != Color.TRANSPARENT)
stillBorder = false;
else
PaddingTop++;
}
}
});
Assuming you are using a nine patch background image, there is a much easier way.
In the nine patch image, you can define a padding box. This padding box will automatically be applied to the contents you set. No need to recalculate the paddings manually in that case.
Note that you should not set a padding on views using a nine patch as a background as the padding from the nine patch will be ignored.

Categories

Resources