I have a button which on start is placed central and 50 pixels from the top of the layout using the following
android:layout_marginTop="50px"
I need to be able to change this margin depending on what background is being displayed to 100 pixels.
any ideas how i change this
There must be a one liner all the answers i can find involve a long layout params method
Any help is greatly appreciated
Mark
Option 1 - Relies on the surrounding/parent layout type, so if the parent layout type is a RelativeLayout, you should use RelativeLayout.LayoutParams instead of LinearLayout.LayoutParams:
LayoutParams params = new LayoutParams(
LayoutParams.WRAP_CONTENT,
LayoutParams.WRAP_CONTENT
);
params.setMargins(0, 100, 0, 0);
myButton.setLayoutParams(params);
//myButton.requestLayout();
Option 2 - Uses a generic method that doesn't rely on the surrounding/parent layout type:
public static void setMargins (View v, int left, int top, int right, int bottom) {
if (v.getLayoutParams() instanceof ViewGroup.MarginLayoutParams) {
ViewGroup.MarginLayoutParams p = (ViewGroup.MarginLayoutParams) v.getLayoutParams();
p.setMargins(left, top, right, bottom);
v.requestLayout();
}
}
Usage:
setMargins(myButton, 0, 100, 0, 0);
this is for your reference...
i hope it will help full to you...
and the best use is dp supports for all device and its density pixels
px
Pixels - corresponds to actual pixels on the screen.
in
Inches - based on the physical size of the screen.
mm
Millimeters - based on the physical size of the screen.
pt
Points - 1/72 of an inch based on the physical size of the screen.
dp
Density-independent Pixels - an abstract unit that is based on the physical density of the screen. These units are relative to a 160 dpi screen, so one dp is one pixel on a 160 dpi screen. The ratio of dp-to-pixel will change with the screen density, but not necessarily in direct proportion. Note: The compiler accepts both "dip" and "dp", though "dp" is more consistent with "sp".
sp
Scale-independent Pixels - this is like the dp unit, but it is also scaled by the user's font size preference. It is recommend you use this unit when specifying font sizes, so they will be adjusted for both the screen density and user's preference.
Related
I'm searching for a way to keep view size proportioned on all devices. I experimented with many maths calculations (e.g. mixing screen size, density, percentage, etc.) but haven't found any solutions, just different results for each device tested.
Let me present an example: Suppose I'm testing an app on a sw-360dp and eventually I find a size view that works.
relativeLayoutParams.width = 150;
relativeLayoutParams.height = 250;
This has the effect of creating a view with size about 1/3 of screen width and 1/2 screen height.
How can I dynamically arrive at value for width and height, that lets the view keep the aspect ratio of 1/3 width to 1/2 height? At least I think that's what the documentation is suggesting when it says: "calculate exact view size (or margin, padding, etc.) from a percentage of screen size".
Or have I misinterpreted it?
Any help will be appreciated.
You can get the device screen size and there by define the ratio,
Display display = getWindowManager().getDefaultDisplay();
Point size = new Point();
display.getSize(size);
Then,
width = (int) size.x * 1/3 ;
height = (int) size.y * 1/2 ;
when declaring some element (let's say a Button) and giving it some width and height (let's say 200dp) from the XML file, I got certain result when running, although when make the same steps but Programmatically I got much smaller width and height, and this case happens only with me in Nexus tablets.
If you set the size of a View programmatically, many times pixels are taken as an argument. You will need to convert your desired size in DPs to pixels first, and use those to set the width or height of your element:
float dp = 200;
float px = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, dp, getResources().getDisplayMetrics());
See the API-docs of the specific Views for infos about what kind of dimensions are taken as an argument.
From PopupWindow Docs :
public PopupWindow (int width, int height)
Added in API level 1
Create a new empty, non focusable popup window. The dimension of the window must be passed to this constructor.
The popup does not provide any background. This should be handled by the content view.
Parameters
width the popup's width
height the popup's height
Question: does the width and height is in pixels (px) or Density-independent Pixels (dip) ?
Bonus Question: how can the PopupWindow achieve Multiple Screen Support ?
The width and height parameters are specified in pixels (px). If you want to convert to density independent pixels (dp), you can use the following:
TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 65, getResources().getDisplayMetrics());
Where 65 is replaced by the number of density-independent pixels. This returns the number of pixels which you can then give to PopupWindow.
I am new to Android. I like having the free range of drawing objects where ever I want. So i have been using Absolute Layout. I get a message saying to use a different layout. And I have read that this is because of the different res of different phones. My question is, is this the only reason in not using Absolute Layout? I have made a method that uses metrics to adjust the pixels.
public int widthRatio(double ratioIn){
DisplayMetrics dm = new DisplayMetrics(); //gets screen properties
getWindowManager().getDefaultDisplay().getMetrics(dm);
double screenWidth = dm.widthPixels; //gets screen height
double ratio = screenWidth/100; //gets the ratio in terms of %
int displayWidth = (int)(ratio*ratioIn); //multiplies ratio desired % of screen
return displayWidth;
}
//method to get height or Ypos that is a one size fits all
public int heightRatio(double ratioIn){
DisplayMetrics dm = new DisplayMetrics(); //gets screen properties
getWindowManager().getDefaultDisplay().getMetrics(dm);
double screenHeight = dm.heightPixels; //gets screen height
double ratio = screenHeight/100; //gets the ratio in terms of %
int newHeight = (int)(ratio*ratioIn); //multiplies ratio by desired % of screen
return newHeight;
}
//sets size of any view (button, text, ...) to a one size fits all screens
public void setSizeByRatio(View object, int width, int height){
LayoutParams params = object.getLayoutParams();
params.width = widthRatio(width);
params.height = heightRatio(height);
}
So if i say setSizeByRatio(Button, 10, 25); It will set the buttons width to 10% of the width of the screen and the height to 25% percent of the screen.
Are there any phones that Absolute Layouts do not work on? Does this layout cause any other issues?
The reason why the AbsoluteLayout is deprecated is because you have alternatives in the LinearLayout or the GridLayout that does the same and more. It seems that you are trying to calculate positions based on absolute positions and number of pixels, an approach that should in general be avoided due to issues with varoius screen sizes and densities.
Read the link that #amiekuser provided and focus on the understanding how the best practice is. Some hints are creating images for ldpi, mdpi and hdpi folders, using the unit for dpi (density independent pixels) instead of raw pixels and how to test your app on multiple screen sizes and densities using the emulator.
Edit:
To set the x- and y-position of a View you must use LayoutParams. See this question on how to to set the TopMargin and LeftMargin for a View using LayoutParams.
Android phones comes in many form factors i.e. not only it varies greatly in terms of screen size(2.7", 3.2", 3.7" ....) but also in terms of resolution (480X800, 480X848 etc).
Google itself suggest not to use AbsoluteLayout. in fact its deprecated in the newer api versions.
The link below explains all these in details:
http://developer.android.com/guide/practices/screens_support.html
Check the best practices section.
I believe you can set layout_width and layout_height to textview element dynamically using something like:
LayoutParams lparams = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.FILL_PARENT);
centimeterLayout.addView(textview, lparams);
But - how do I set the layout width and height in other units - e.g. I want to set the layout width of my text view to 20 mm. How do I do that?
LayoutParams either take one of the constants (FILL_PARENT, WRAP_CONTENT) or a pixel value. Since you want to use millimeters, you have to convert a millimeter dimension to a pixel dimension. Doing so is pretty easy:
Resources r = getResources();
float px = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_MM, 20,
r.getDisplayMetrics());
In this example, 20 mm are converted into a pixel dimension that you can use in your LayoutParams. You can use other dimensions too, such as TypedValue.COMPLEX_UNIT_DIP for dp/dip¹. Just change the constant in the arguments. The android doc has a list of useable dimensions.
¹ Density independend pixels, a highly recommended dimension that adjusts to the many different screen sizes and densities. Using mm isn't the best way to do things, since your text will probably look okay on a big screen and fill a big portion of a small screen, or the other way around - which is not ideal. I also recommend sp for font sizes. See the dimension list for details.