I am having some difficulty with an Android layout problem. I am trying to make a form for users to fill out. This form is defined programmatically (from a server-provided configuration over which I have no control) and thus I must implement it programmatically. The form has several different field types, but for simplicity we can assume they are all simple text fields (EditText).
I currently have the form implemented as a vertical LinearLayout. For each field I have a horizontal LinearLayout that contains a TextView for a field label and an EditText for the user to enter a value for the field. I have the EditText set to fill the width using LinearLayout.LayoutParams(FILL_PARENT, WRAP_CONTENT).
This works well when the TextView label is short, but when it is long it causes the EditText to be very small and makes it hard for the user to enter a value. Ideally I would like the EditText to be at least half the width of the screen with the TextView label wrapping if necessary. I've tried a TableLayout with TableRows but I still had difficulty. I would also rather not force a grid and thus waste the space on the lines with short labels (assuming the other requirements are met I'm flexible on this). I would have tried something like a FlowLayout to force the EditText to wrap onto the next line but it's not supported on Android.
Any suggestions for how I can make this work better? XML-based solutions will be accepted assuming I can port them to a programmatic approach. I would also like to make this as flexible with respect to screen size and orientation as possible, so this means avoiding hard-coding any widths.
Thanks in advance.
Try playing around with layout weights. You should be able to tell your two items to each take up half the screen, for example, by setting the width=0 and layout_weight=1 for both.
Related
I'm making a chat for Android and I need to make a main xml layout.
There is going to be a TextView to display history, EditText and Send Button. All view should be positioned like in whatsapp. EditText and Button at the bottom of a screen. The rest of the space goes to the TextView.
So how is it possible to do it, so it would look nice at any screen and any orientation?
I tried to do it with android:layout_weight, but I don't think it's going to be very portable.
Thanks in advance.
I don't think a single TextView is the best way to achieve this.
I'd recommend using a ListView instead of a giant TextView to hold the entire conversation history. Each element in the ListView would hold a single TextView and any other required views to display each message in the history, and it will by default allow for scrolling up and down to view the entire history. You can then just adjust the text size to handle different screen sizes.
This is how the default Android Messaging app is implemented, but you can customize each item in the ListView to make it look how you want (like WhatsApp, for example).
Hope this helps.
because layout_weight sets the proportions, but the height of my editText/Button is fixed
So? Don't put android:layout_weight on the fixed portion.
So for different screen sizes, diffrerent height would be given to them, leaving some space.
Then don't put android:layout_weight on the fixed portion. You are hitting yourself on the head with a hammer, then complaining that your head hurts.
Step #1: Vertical LinearLayout.
Step #2: Transcript TextView inside the LinearLayout, with a height of 0 and a weight of 1.
Step #3: EditText and Button (in a horizontal LinearLayout?), inside the vertical LinearLayout, with a height of wrap_content and no weight specified (defaults to 0).
Your fixed-height stuff, with a height of wrap_content, will get its allocation of pixels, and your transcript TextView will get all remaining pixels, courtesy of its weight of 1.
I also echo physphil's suggestion to use a ListView in transcript mode for your chat transcript, rather than the TextView.
i'm trying to layout a fairly basic screen. it's just a details view screen after a list item click.
initially i'm looking to acheive a side by side stacked label value type of screen.
for example, where to the left of colon is static text and to the right of colon being dynamic values based on row clicked.
first name: john
last name: doe
last login date: yesterday
additional info: blah
i've started with a relative layout with a bunch of text views in it all positioned accordingly to acheive something like what i was looking for.
The problem arises when the dynamic data being displayed grows and stretches its enclosing text view. Of course the static labels don't grow and everything gets mis aligned...
I'm wondering if there is a different way of tackling this sort of layout...
i was shying away from stacking a bunch of horizontal linear layouts inside a vertical linear layout.
is table layout the way to go? i've read that "they usually aren’t the best tool for doing so, as they are derived from LinearLayout and not the most efficient of layout controls".
Yes there is. Use a listview with a layout predefined in xml. Use a simplelistadapter and pass it the dataset that you want to populate it with.
Edit
Here is a great tutorial:
http://www.vogella.com/articles/AndroidListView/article.html
For a simple form like you want to create I'd suggest using a TableLayout. It is simple to use. As you said the alternative to a TableLayout would be horizontal LinearLayouts in a parent vertical LinearLayout. Using a TableLayout will also automatically align the right side dynamic content for you. Everything on the right side will be treated as a column so if one resizes, they all resize to match.
In your particular scenario I would believe that the TableLayout would work well (although I have also heard similar issues of efficiency/performance). As long as the entire Viewgroup of this Activity isn't complex, I don't think the performance will be too noticeable.
If you are attempting to make the RelativeLayout version work, perhaps you can try this: Have all of your static labels are aligned to the left using android:layout_alignParentLeft and have each aligned to the top of the dynamic TextView they are corresponding to using android:layout_alignTop. This should keep the static TextViews aligned to the left while aligned to the dynamic view relative to it.
Now that those views are aligned, we can horizontally align the dynamic views to the longest static TextView using android:layout_toRightOf. From there, all the remaining dynamic views can also android:layout_alignLeft to this anchor dynamic TextView, or also align to the longest static TextView in the same manner that the anchor was. This solves the horizontal alignment of all the dynamic TextViews.
Finally, we can set that each dynamic TextView falls under the next, since the dynamic TextViews are our determining our vertical location within this RelativeLayout. Each view can use android:layout_alignBelow to chain the fields to align vertically.
I believe this should work for you and I can edit this post later in the day if you would like a sample of code.
Is there any way position views relative to each other like you can with Android layouts?
Example: You have two UILabels that are dynamically set to strings of variable length, one above the other, and you want the bottom label to appear directly below the last line of the top label, regardless of how many lines the top label ends up having.
Another example: Same situation as above, but one of the labels is sometimes hidden. You want the resulting label(s) to be centered vertically in the parent, regardless of whether it's one label or two labels.
Android's Linear Layout and Relative Layout make this very easy to do, but I can't figure out how to do this is iOS. Can it be done?
You will be able to do this using AutoLayout in iOS6. For an application that should run in iOS before 6.0, you have to do it by yourself, but this is not very complicated.
Actually I have implemented a class to do this (that's a long time ago, I hope it still works, but there is no reason not to). This OHStackView class is a subclass of UIView that automatically layout its subviews horizontally or vertically to stack or align them.
You can ask OHStackView to stack its subviews horizontally or vertically (one above the other, etc), or align their top/bottom/left/right borders or their centers, and even specify a padding between each subviews. Each time one of the subview changes its frame or size, OHStackView will automatically relayout all depending views to realign everything.
(E.g with your two UILabels, a simple call to sizeToFit on your labels to make them adjust their size to their content will relayout everything around automagically)
There is an example project provided so feel free to test it.
Note: IIRC, my subclass does not take the "hidden" property of the subviews into account. But you can easily add support to this behavior by adding a condition like if (v.hidden) continue; in the for loop of its layoutSubview implementation to only take non-hidden views into account in the layout algorithm.
HTH
I've been searching if it's possible for a long time. As far as i can tell, it's not possible for now. I don't remember where i read this,but it will be possible with ios6. Instead of using Android's Linear Layout,you can use sizeWithFont method to detect size of your UILabel,then you can set their frame to position them.First,you need to set their text of course to find their size according to their font family. Another thing you can use is sizeToFit method. Unfortunately,i don't know how to use it. You can give a shot,though. At that time,i found this.Maybe ,you can use it https://github.com/scalessec/CSLinearLayoutView
My goal is to create an automatic form generator, so the user can add controls to the screen. And the controls must have different widths.
Example:
The user could add an EditText that will use the width of the screen and add a CheckBox after the EditText that would be placed below the EditText. And could also add a button or spinner that will use the rest of the width of the screen. The user can all all the controls desired.
How can i achieve this goal?
Instead of a gridview, you could use a TableLayout, which has multiple TableRow elements.
What's interesting is that the width of a column is defined by the width of the widest element in the column.
You can take a look at the TableLayout documentation for more info.
There are a number of ways to do it such as TableLayout and also using lots of nested layouts.
The TableLayout way is probably the best and easiest way to implement what you're looking for.
If you want to dynamically change the layout depending on the width of the screen there are two ways.
Method 1 Programmatically create the layouts instead of using xml layout files. this way you can do calculations and change things on the fly.
Method 2 This is probably the way I would do it. Include different layout files for different screen densities, orientations and sizes.
I have a very simple layout with two side by side textviews. Both have the same parent layout that fills the screen horizontally.
I need them to have a visible space between them so that they are visually seperated when both have text. I also need the left textview to take up about 2/3 the screen width and let the other have the rest.
This is fairly easy to do with LinearLayout and a few margin settings, but if either one of the views has no text, I need the other one to fill the entire width.
I'm not quite sure how to have the layout do that without setting the empty view's visibility to GONE in code. Is there any good, efficient way to do all of these things at once? Feel free to use any layout you wish to make it work.
have you tried this using a relative layout? there is a property for layout_alignWithParentIfMissing that might give you what you need...