I am trying to align a custom View object above and aligned_left of a RelativeLayout. My (snipped) code looks something like this:
int bored = board.getId(); //board is the RelativeLayout
Border border = new Border();
RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
params.addRule(RelativeLayout.ALIGN_LEFT, bored);
params.addRule(RelativeLayout.ABOVE, bored);
this.addView(border,params);
This gives me a Border object aligned_left with my RelativeLayout but NOT "ABOVE" (technically, it is above it, but it's at the top of the screen not aligned the way it's supposed to be). And, even stranger, when I do this:
int bored = board.getId();
Border border = new Border();
RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
params.addRule(RelativeLayout.ALIGN_LEFT, bored);
params.addRule(RelativeLayout.BELOW, bored); //<---The only difference
this.addView(border,params);
...it works perfectly. it is aligned left and below in the ways that are expected. Why is the ABOVE attribute giving me such a hard time?
Edit:
ABOVE is supposed to align the bottom edge of one view with the top edge of the target. Here is a screen shot of how my project is not working as intended.
The green bar at the top of the screen is the Border object I am trying to align. As you can see, its left edge is aligned with "board" however it is in the wrong place at the top of the screen.
Can you check if board and Border are not using more space? for example, by setting the background to a color to see their dimensions in the screen?
Maybe board, which you mention is a RelativeLayout is bigger of what you think.
I hope this helps
I fixed my problem by using an ImageView instead of my custom Border class (which was basically just a bitmap drawn to a canvas from a resource). My code now looks like this:
int bored = board.getId(); //board is the RelativeLayout
ImageView border = new ImageView(this);
border.setImageResource(R.drawable.border_tiki1);
RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
params.addRule(RelativeLayout.ALIGN_LEFT, bored);
params.addRule(RelativeLayout.ABOVE, bored);
this.addView(border,params);
My best guess is that it was having trouble defining the ABOVE constant for my custom object. Thanks to everyone who took the time to look over this. Here's what my view looks like now:
From this anchor, I'll build the rest of the border out of other small pieces. Thanks again!
Without seeing the rest of the code, this is just a guess, but the order in which the objects are created makes a difference in how the objects are layed out. Especially where Relative Layouts are concerned.
Related
I want to change the height of a LinearLayout and works everything OK, but I want height decreasing and increasing from the top (the defaults starts decreasing and increasing from the bottom).
Here is an example:
LinearLayout linearLayout = findById(R.id.layout);
LinearLayout.LayoutParameters layoutParams = (LinearLayout.LayoutParameters) linearLayout.getLayoutParams();
layoutParams.height = linearLayout.getHeight() - 1;
linearLayout.setLayoutParams(layoutParams);
This works OK. The only thing I wanna change is the direction of height change.
Thanks for the replay.
You can achieve this by binding(the bottom) of your linear layout inside a constraint layout,
Also is there a parent to your linear layout?, if so then it being unbound might be the reason
I achieved changing the direction with the setLayoutDirection(View.LAYOUT_DIRECTION_LOCALE) from teh ViewGroup class. Also had to change layout's gravity to bottom in the xml.
Thanks for contribute to my answer.
Right now I am trying to solve a problem with adding views on top of a custom view that can exceed the screen bounds. That custom view draws different rectangles at different angles. For later use it should be possible to select the rectangles for later drag n drop implementations where I don’t want to constantly redraw the whole custom view.
So over each drawn rectangle I put a button that has the same dimensions and rotation.
For some reason however android seems to resize my views automatically when it hits the end of the Screen:
My expectation(button covers everything even if only half visible):
The actual behaviour(button gets shrunk):
This by itself is not a huge issue when the view I want to add is not rotated.
If the view is rotated however the rotation around the center point causes all kinds of problems as the view is now smaller and on a different location:
My expectation(button is rotated exactly around the center point of the object):
What I get is button becomes smaller and therefore its center point moves:
I read on other questions that View.setClipChildren(false) and View.setClipPadding(false) should help. But all it does is basically mess up my view hierarchy because I kinda want clipping to happen but not the automated resize. And on top of that it doesn’t fix the issue that I am having.
Does any of you have an Idea how I can fix this?
I tried to do the same on IOS and JavaFX which both work as I expected them to.
Since I am trying to solve the whole thing programmatically, I created some test code that places a buttons center point on the screen edge and rotates it 45 degrees: So you should only be able to see half of the button. But the button appears smaller and is fully visible on the right side of the screen. Of course due to the different center point it’s also not on the location I would expect it to be.
public class MainActivity extends Activity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Context context = getApplicationContext();
RelativeLayout relativeLayout = new RelativeLayout(context);
DisplayMetrics displaymetrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(displaymetrics);
int height = displaymetrics.heightPixels;
int width = displaymetrics.widthPixels;
Button button = new Button(context);
button.setText("DO STUFF");
RelativeLayout.LayoutParams params = new RelativeLayout.LayoutParams(800, 80);
params.leftMargin = width - 400;
params.topMargin = height / 2;
button.setLayoutParams(params);
button.setRotation(45);
button.setBackgroundColor(Color.RED);
relativeLayout.addView(button);
setContentView(relativeLayout);
}
}
I found the solution myself by accident.
It appears to be a special behavior of the RelativeLayout. I didn't find anything that explains it, but I swapped it out with a FrameLayout which has two positive effects.
It works as I expected it to
I got a performance increase since I was also nesting multiple Relative Layouts into each other.
I am aware that there are a lot of questions out there with a similar question. However, most of them deal with horizontal orientation whereas my problem is with vertical orientation. And I have tried a few but they were of no help.
I am having issues with vertical orientation of linear layout. I have got this so far:
My layout parameter for this is as follows:
LinearLayout.LayoutParams lparams = new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
lparams.weight = 1;
// And then simply adding this Layout param to all the widgets
However, when I set the height property to 0, I get nothing. My understanding is I should still get the same output since it should be assigning equal height to all of them based on the weight property. Can any one please help out?
I have finally figured out the problem. The problem was not with my understanding. My understanding is correct. However, when setting the content view I was passing in the same LayoutParams that I used for widgets. When, I set the height to 0, it would all set the height of everything to 0. To get around it, I just needed to create a new LayoutParam and pass that in with Content View.
I have an ImageView and I want to change it's size in runtime. So I do the following:
LayoutParams params = (LayoutParams) imgView.getLayoutParams();
params.width = size;
params.height = size
imgView.setLayoutParams(params);
The problem is that based on these new width and height I want to change my another ImageView, but seems like LayoutParams are not applied immedately, because Log put just after setLayoutParams prints old width value. So here is a question: is there any way to force ImageView to update (I already tried View.invalidate() and View.requestLayout but no success), or is there any way to detect if ImageView has finished updating, so I can use it's new parameters?
you can attach a viewTreeObserver. Which will get called every time layout is changed
You can follow this link
I'm new to Android but i have a simple problem.
I have a vertical linear layout, if i place here a normal button, and give it the MATCH_PARENT flag for the width and the height, the button will fill all the space. All ok.
Now i have a my simple custom view (a class that extends View) and i overrided the OnDraw method for draw a cross in the middle of the view. For draw the cross i need to get the width and the height of the control, if in the UI Layout editor of eclipse i set a fixed width and height, it works correcly (i see a preview of the cross directly in Eclipse) but if i extend the View to the borders i got only WARP_CONTENT (With button i get MATCH_PARENT), no problem, i change it in the XML, but LayoutParams width and height will return 0!! (I see the error directly in the preview of eclipse!) Why?
I tried to set manualy the width and the height in the OnWindowFocusChanged method to wait but it give me always 0.
The problem is that the view actualy have the rights dimensions but when i call the getLayoutParams().width it give me 0, so i see a white rectangle in the right position (white background of the view), but the cross is drawed on the upper-left corner!
Sorry for my bad english.
Thank you.
Mauro.
i think u need to set this parameter for your view.
android:layout_alignTop
or something related to this.i guess