Concatenating layouts during runtime - android

I am thinking to create a layout whose height is much more than the screen height. OK say, the parent layout is LinearLayout and it is set to provide a vertical scrollbar automatically.
Inside the parent layout, there are many controls (listview, gridview, listboxes, editboxes etc). To make it easier for design, can I put listview in one xml, gridview in one xml, listbox in one, editbox in one etc and then later use some defined function to concatenate and allocate them all in the parent layout ?
If this is not possible, how can I design a layout that has many controls allocated that design screen can't fit at design time ?

xml_common.xml
code:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="#dimen/common_topheader_width"
android:background="#drawable/topheaderfor9patch" >
<ImageView
android:id="#+id/xml_common_header_imageLogotop"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_centerVertical="true"
android:layout_marginLeft="2dp"
android:layout_marginRight="#dimen/common_left_right_margin"
android:src="#drawable/qarrow" />
</RelativeLayout>
///////////////////////////////////////////
Main_view.xml
Code:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#drawable/mainbg"
android:orientation="vertical" >
<include layout="#layout/xml_common" />
</LinearLayout>
you can set different images as per your choice set in runtime of common view.

Related

How to add flexible sizing to layout components of android

Is there any way to add flexible sizing attributes to in XML of android layout.
I want to add elements such that the height/width of one element equals to height of parent minus another element.
Like in CSS, we can use calc() function
Ex: calc(100% - 100px)
Is there a way to do something similar in android, like:
I set
android:layout_height="?attr/actionBarSize"
So, is there anything like:
<RecyclerView
android:layout_height = "(match_parent - ?attr/actionBarSize)"/>
Is there any way to achieve this in XML itself and not with java in the activity?
No there is not. But you can do it by using margins.
For example if you need to "cut" the height of a RelativeLayout from bottom you can use:
android:layout_marginBottom="?android:attr/actionBarSize"
or if you want to do it from the top:
android:layout_marginTop="?android:attr/actionBarSize"
Yes you can do that in Relative layout as below
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/linear_layout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<Button
android:id="#+id/button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true" />
<ListView
android:id="#+id/listview"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_above="#+id/button" />
</RelativeLayout>
As in above code first i placed button at bottom.Now for remaining place i want to display listview. So i place listview above button and make it match_parent.So it will all remaining space.

Stop views overlapping horizontally in a relative layout

I have two views, a day view and a event view as part of a calendar. I want my events to fill the day view in width (which is working) but when I add another at the same position/time I want them to split the width... I am adding my event dynamically using java. Is there an attribute I can use so that views don't overlap?
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:id="#+id/dayView"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#drawable/day_view">
</RelativeLayout>
.
<?xml version="1.0" encoding="utf-8"?>
<ie.test.calendar.CalendarEventView
xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:id="#+id/eventView"
android:background="#drawable/event_view"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/eventTextView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingTop="3dp"
android:paddingBottom="5dp"
android:paddingLeft="5dp"
android:paddingRight="3dp"
android:textAppearance="#android:style/TextAppearance.Medium"
android:textColor="#android:color/white"/>
</ie.test.calendar.CalendarEventView>
I think you need to use Linier layout as parent view with horizontal orientation. And also use concept of weight for width. It will devide your parent view according to child quantity
Take a look on RelativeLayout.LayoutParams
You could set rules at runtime, using ID's.
layoutparams.addRule(RelativeLayout.ALIGN_RIGHT, R.id.id1)
Although, i think, that using LinearLayout would be much simpler.

How to make several RelativeLayouts each occupying a potion of the screen?

I want to have a relative layout inside another full-screen relative layout, occupying full width but 50% of its parent's height, preferably done with XML and not java code.
I have figured out how how to align parent's center, and how to fill up the width, but is there a way to get 50% of parent's height? What about 30%? 6.2834%?
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent" android:layout_height="fill_parent">
<RelativeLayout
android:layout_width="fill_parent"
android:layout_height="??????????"
android:layout_centerInParent="true" >
The reason I'm trying to do percentage is that, if I specify it with "dip", while the object will remain the same size, the layout will look a lot different on different screen sizes (e.g. a phone and a tablet).
EDIT:
Thank you for all the answers about using LinearLayout and weighting. I have looked at that before, too. I feel I might have over-simplified the problem. Say I need something like this:
I suppose I could use complicated LinearLayout and weighting to outline the center square, then having the center square to fill_parent, like so:
But then what should I do with the other 3 squares (layouts)? Can I have another "layer" of LinearLayout for another square? Or should I divide up the whole screen into many, many small cells and having these sublayouts span over multiple cells (not sure if this is even possible)?
Try to use LinearLayout with weightSum
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:weightSum="2"
android:gravity="center_vertical"
android:orientation="vertical" >
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:background="#FF0000">
</RelativeLayout>
</LinearLayout>
If you don't absolutely need it nested in one RelativeLayout you can use weight in a LinearLayout as others have pointed out. I just added in an additional RelativeLayout above and below so you can use the rest of the screen if you are trying to. If not, just remove the other RelativeLayouts.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/ParentLinearLayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
android:weightSum="10" >
<RelativeLayout
android:id="#+id/RelativeLayoutTop"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="2.5"
android:background="#color/torange" >
</RelativeLayout>
<RelativeLayout
android:id="#+id/RelativeLayoutMid"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="5"
android:background="#color/tpurple"
android:padding="8dp" >
<TextView
android:id="#+id/description"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true"
android:text="#string/describe"
android:textAppearance="?android:attr/textAppearanceLarge" />
</RelativeLayout>
<RelativeLayout
android:id="#+id/RelativeLayoutBottom"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="2.5"
android:background="#color/torange" >
</RelativeLayout>
I usually go with a LinearLayout for this and set the weight to a certain percentage :
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical">
<View
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="25"/>
<RelativeLayout
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="50">
</RelativeLayout>
<View
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="25"/>
</LinearLayout>
To your edit:
At some point you need to determine the layout. Start by taking the layout in groups. Look for patterns. In your simple explanation we have devised a way using a linearlayout to group 3 objects with one in the middle. With your new layout, could you group those items in any way?
Once you have simple layout patterns set, maybe add specific spacing that you are looking for by defining weights. Then you might want to add a relative layout and start anchoring views to specific views. Ask yourself do they overlap? Does one view always position on top of other views or on the sides. What defines the bounds of your views and then take it from there using linear layouts, weights, relative layouts, toLeftOf, toRightOf, bellow, above, margins, and padding.
Here is an example of what I mean by grouping like objects. It's by no means the best solutions but that all depends on how you define the positioning parameters.
Yellow = vertical linear layout
Green = horizontal linear layouts
You have 1 large vertical layout and inside two horizontal layouts with multiple objects inside of that. From there you can break it down into easier to manage portions on how to arrange and item within that layout. Now with relative layouts you could position items relative to another object, you could remove some of the work handled by the linear layouts but you will then be defining their distance relative to the other objects and might have to fiddle to get the layout to adjust properly on different screen sizes (reason to not use static positioning).
Maybe try using a LinearLayout with 3 layouts inside with android:layout_weight set to 1, 2, 1.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical" >
<RelativeLayout
android:background="#FF0000"
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="0dip" >
</RelativeLayout>
<RelativeLayout
android:background="#00FF00"
android:layout_weight="2"
android:layout_width="match_parent"
android:layout_height="0dip" >
</RelativeLayout>
<RelativeLayout
android:background="#FF0000"
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="0dip" >
</RelativeLayout>
</LinearLayout>
RelativeLayout does not support percentage of width and height for children. Use LinearLayout with android:layout_weight attribute.

Android - how to add a simple footer?

I keep browsing different posts and they all have the footer try to stay on the screen.
But I want the footer to appear on every page. Some of my pages do not have a scroll, but some do. Whenever there is a scroll, I would like the footer to appear below the scroll. How can that be done?
For example, if I have this page:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
>
<ScrollView
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<LinearLayout
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
>
<TextView
android:id="#+id/page_exlain"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="Some text that either extends far down or is pretty short."
android:layout_marginTop ="20dp"
/>
</LinearLayout>
</ScrollView>
</LinearLayout>
What is a good way to add a footer to this that does not necessarily appear above the fold?
Thanks!
My way of doing this is by having two linear layouts inside the parent layout. The first one is what I call the content area and will have a weight of 1, meaning it will try to take as much space it can from the parent view. The footer layout on the other hand will have no weight and will therefor remain with a height matching the content inside even if the other view (the content area) is empty.
You can add a scrollview or any other type of layout inside the content part of this layout without breaking the disposition of the two elements and without needing to worry about the position of the footer since it will always be at the bottom of the screen.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/main"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical" >
<LinearLayout
android:id="#+id/content"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:orientation="vertical" >
</LinearLayout>
<LinearLayout
android:id="#+id/footer"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
</LinearLayout>
With a little content added to the prior code, you end with something like this, note that it's extremely simplified. You'll have no issues modifying it to your needs as long as you understand the weight property in place.
You just need to treat the "content" LinearLayout as if it was the parent one, inserting scrollviews or whatever your needing and forgetting about the footer. Note that if the footer is recursive, meaning you are going to be using it multiple times, you could load it in the xml directly without copying it in to all your layouts
<include layout="#layout/footer" />
Where #layout/footer is an xml file in your layouts folder with the content of the footer that you want to reuse. This is virtually the same as adding it manually but with the convenience of not having to maintain it across several files.
Hope I was of help.

Visible and Invisible Layouts

I need your advice regarding my design and if you have a better idea (or you agree with me) that it is good. for some reason I have a feeling it is a "stone age programming style" but lets see.
Basically I have my xml relative layout. In the center (vertical and horizenatlly). I want to display "either" 3 buttons OR 3 texts depending on some user input. So what I did is the following:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/mainLayout"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:clipChildren="false"
android:clipToPadding="false" >
<RelativeLayout android:id="#+id/Buttons"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true" >
<Button1 .../>
<Button2 .../>
<Button3 .../>
</RelativeLayout>
<RelativeLayout android:id="#+id/Texts"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true" >
<TextView1 .../>
<TextView2.../>
<TextView3.../>
</RelativeLayout>
</RelativeLayout>
Depending on the user input in the code I set visibility to either Visible or Invisible
Is this alright? and if not what do you suggest?
What you need is View.GONE, and View.VISIBLE.
With View.GONE - the layout doesn't occupy any space (almost as if it didn't exist at all). If you use View.INVISIBLE, to the user, the view (buttons, or text in your case) will not be visible, but they will still be there on the screen, thus shifting the other view (buttons, or text) up or down (the view won't be in dead center).
TIP: You can use 'android:layout_centerInParent' instead of 'android:layout_centerHorizontal' and 'android:layout_centerVertical'.
In my opinion, what you have done may be primitive, but it is simple, which is good :) But if you still want some options and make life complicated, then
Put each of the blocks in a separate xml and use include.
Make 2 views and then use ViewFlipper to flip them based on user requirements.
But for the simple requirement that you have, I think u r doing fine.
The include option would work something like this,
layout_1.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/Buttons"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true" >
<Button1 .../>
<Button2 .../>
<Button3 .../>
</RelativeLayout>
layout_2.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/Texts"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_centerHorizontal="true"
android:layout_centerVertical="true" >
<TextView1 .../>
<TextView2.../>
<TextView3.../>
</RelativeLayout>
your main_layout.xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/mainLayout"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:clipChildren="false"
android:clipToPadding="false" >
<include layout="#layout/layout_1" />
<include layout="#layout/layout_2" />
</RelativeLayout>
The include helps you in making reusable layouts and also helps in keeping your xml files grow out of proportions, specially when you have complicated UIs.
First option is:
You can add all the three buttons or textviews in Linearlayout and center it in parent by using android:layout_centerInParent.
Second option is:
You can center the middle button out of all the three buttons and adjust the other two buttons with respective to the middle button. Same way we should also repeat this for textviews. In this option, we should make all the three views visibility to View.GONE explicitly.

Categories

Resources