I want to decompose my UI into several XML Layouts. The first one would be the main layout, and the other ones would be the content layouts.
I would like to be able to set which content_layout should be included dynamically at run-time, so I don't want to set a "layout="#+layout/content_layout" in my XML file.
Here are my layouts:
main_layout.xml:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="600dp"
android:layout_height="800dp" >
<TextView
android:id="#+id/title"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_alignParentTop="true" />
<include /> <!-- I WANT TO INCLUDE MY CONTENT HERE -->
<Button
android:id="#+id/cancelButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_centerHorizontal="true"
android:text="Cancel" />
</RelativeLayout>
content_layout.xml:
<?xml version="1.0" encoding="utf-8"?>
<ListView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/whatever"
android:layout_height="wrap_content"
android:layout_width="fill_parent" />
content_layout2.xml:
<?xml version="1.0" encoding="utf-8"?>
<ListView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/whatever2"
android:layout_height="wrap_content"
android:layout_width="fill_parent" />
How can I do that?
Thanks!
<RelativeLayout android:id="#+id/rl" ...
In your code:
// get your outer relative layout
RelativeLayout rl = (RelativeLayout) findById(R.id.rl);
// inflate content layout and add it to the relative layout as second child
// add as second child, therefore pass index 1 (0,1,...)
LayoutInflater layoutInflater = (LayoutInflater)
this.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
rl.addView(1, layoutInflater.inflate(R.layout.content_layout, this, false) );
You could try using a ViewStub and just change which layout it is going to inflate programatically.
This answer discusses using one ViewStub.
Related
I want to have 3 layouts in my ScrollView but when I add them it actually doesn't scroll. I tried to put all layouts in different files, then include them, tried to put them in ListView and it doesn't work too. In this option, when I put in ScrollView the LinearLayout and there include the rest of the layouts the application show nothing. That's probably becouse I don't know how to refer to that nested layouts... This is my XML:
activity_main.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="wrap_content"
>
<ScrollView android:layout_width="match_parent" android:layout_height="match_parent">
<LinearLayout android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
>
<include layout="#layout/first"/>
<include layout="#layout/second"/>
<include layout="#layout/third"/>
</LinearLayout>
</ScrollView>
</LinearLayout>
#EDIT views included (all are the same so I put just one):
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/first"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
>
</RelativeLayout>
And in the main activity I put the objects into layouts like this:
setContentView(R.layout.activity_main);
RelativeLayout first = (RelativeLayout) findViewById(R.id.first);
RelativeLayout second = (RelativeLayout) findViewById(R.id.second);
RelativeLayout third = (RelativeLayout) findViewById(R.id.third);
...some code creating views...
first.addView(myView1);
second.addView(myView2);
third.addView(myView3);
Need to put fix size in included layout, for example:
<RelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/first"
android:layout_width="match_parent"
android:layout_height="300dp"
/>
I don`t understand why do you need to add view manually when you already added it to the layout.
You should also eliminate top Linear Layout since there is no use of it.
So I have an xml that consists of a linear layout containing a Button and a TextView like this:
<?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="100dp"
android:orientation="vertical">
<Button
android:id="#+id/btnCell"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="start"
android:paddingLeft="40dp"
android:text="Button"
android:textColor="#color/blueText" />
<View
android:height="wrap_content"
android:width="wrap_content"
android:background="#drawable/Test"/>
</LinearLayout>
And I want to use this same layout inside other layouts in a different xml. I need the same button at every time, so I reuse it by including it in the two layouts (both layouts are in the same xml, but ones is hidden):
First one
<?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:orientation="vertical">
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#drawable/image"
/>
<include layout="#layout/buttonLayout"/>
<EditText
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
Second One:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:visibility="gone"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<EditText
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#drawable/image"
/>
<include layout="#layout/buttonLayout"/>
<CheckBox
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
So I show the first layout and hide the second one at the beginning of the app , as the user moves within the interface, the layouts exchange so that the other one is shown and the first one hidden.
The thing is that I declare the Button in my java activity class like this:
btnCell = (Button) thirdView.findViewById(R.id.btnCell);
btnCell.setOnClickListener(this);
And implemented the listener.
#Override
public void onClick(View v) {
if (v == btnCell) {
System.out.println("entered if");
}
System.out.println("entered function");
}
The problem is that when I click the button when the first view is shown and the second hidden, the button works just fine, but when I unhide the second layout, hide the first one, and proceed to click the button, that should be the same as the first one but in a different layout, nothing happens. I searched and find out, that this happens because the id is assigned only to the button shown in the first layout because of view hierarchy, but not the one in the second layout. How can I make both buttons react to the same action, without declaring a new button in each layout but instead reusing it?
I have used this type of layout. you can create Id different for both and inflate that view and give different name so You can differentiate both thing.
<?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:orientation="vertical">
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#drawable/image"
/>
<include android:id="+id/firstOne" layout="#layout/buttonLayout"/>
<EditText
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
android second one is
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:visibility="gone"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<EditText
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="#drawable/image"
/>
<include android:id="+id/secondTwo" layout="#layout/buttonLayout"/>
<CheckBox
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
The Problem is both the layout are include in same layout file and the id of that
button are same so whenever you click on any of the button at the same time event will fire on both button like both are clicked.
So, you have to give the different id for both the button I hope it works fine..
You can add a different Id for each included layout:
<include android:id="+id/layout_a" layout="#layout/buttonLayout"/>
and
<include android:id="+id/layout_b" layout="#layout/buttonLayout"/>
and then use two findViewById to reach them:
btnCellA = (Button)thirdView.findViewById(R.id.layout_a).findViewById(R.id.btnCell);
btnCellB = (Button)thirdView.findViewById(R.id.layout_b).findViewById(R.id.btnCell);
I have a list that is intended to be below toggle buttons. The list grabs data from a server and then parses them. My XML is as follows:
<?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="wrap_content"
android:orientation="horizontal" >
<ToggleButton
android:id="#+id/toggle_button1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight="1"
android:textOff="Apps"
android:textOn="Apps" />
<ToggleButton
android:id="#+id/toggle_button2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_toRightOf="#id/toggle_button1"
android:layout_weight="1"
android:textOff="VMs"
android:textOn="VMs" />
<ToggleButton
android:id="#+id/toggle_button3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_toRightOf="#id/toggle_button2"
android:layout_weight="1"
android:textOff="Groups"
android:textOn="Groups" />
<ListView
android:id="#+id/mylist"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="#id/toggle_button1" />
</RelativeLayout>
Code for the actual fragment:
public class ProblemFragment extends SherlockListFragment
{
private SeparatedListAdapter list;
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
this.getSherlockActivity().setContentView(R.layout.problem_layout);
list = new SeparatedListAdapter(this.getSherlockActivity(), new Layout(R.layout.separated_list_adapter_two_text, R.id.two_text_title, R.id.two_text_desc));
ToggleButton b1 = (ToggleButton) this.getSherlockActivity().findViewById(R.id.toggle_button1);
ToggleButton b2 = (ToggleButton) this.getSherlockActivity().findViewById(R.id.toggle_button2);
ToggleButton b3 = (ToggleButton) this.getSherlockActivity().findViewById(R.id.toggle_button3);
setListAdapter(list);
refresh();
}
public void refresh()
{
list = new SeparatedListAdapter(this.getSherlockActivity(), new Layout(R.layout.separated_list_adapter_two_text, R.id.two_text_title, R.id.two_text_desc));
refreshStats();
}
public void refreshStats()
{
//Omitted parsing code
list.addSection(new String("Hello world!!"));
setListAdapter(list);
}
}
However, when I use setListAdapter(list), the buttons are overwritten. They are visible before the app retrieves the data and parses it, but they are overwritten after I call setListAdapter. How can i fix this?
First, remove
android:orientation="horizontal"
from your root layout. RelativeLayout doesn't have an orientation property. Also, weight is for child elements of a LinearLayout and when you use it then you should assign the width of each child view to 0dp for horizontal orientation and height="0dp" for vertical orientation.
Then wrap your ToggleButtons in a LinearLayout, vertical or horizontal orientation, and give it the property
android:layout_alignParentTop="true"
then give your ListView the property
android:layout_below="#id/idOfLinearLayout"
So it may look something like
<?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="match_parent" >
<LinearLayout
android:id="#+id/toggleLL"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentTop="true">
<ToggleButton
android:id="#+id/toggle_button1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textOff="Apps"
android:textOn="Apps" />
<ToggleButton
android:id="#+id/toggle_button2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textOff="VMs"
android:textOn="VMs" />
<ToggleButton
android:id="#+id/toggle_button3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textOff="Groups"
android:textOn="Groups" />
</LinearLayout>
<ListView
android:id="#+id/mylist"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="#id/toggleLL" />
</RelativeLayout>
I also removed the RelativeLayout properties from the ToggleButtons since they are now wrapped in a LinearLayout. And you had a circular view error there with assigning the second ToggleButton to the right of itself which may have been a copy/paste error. Hope this helps.
Note that the default orientation for a LinearLayout is horizontal so leaving that property out will give you that effect.
Oh! I can not test your XML but I think that you need scrollbars! If the list is filled with a lot of entries, it can became bigger that the screen, making the buttons disappear because they are pushed up by the list. Try to add a scroll to the whole layout.
Something like this:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent"
xmlns:android="http://schemas.android.com/apk/res/android">
<ScrollView
android:layout_width="wrap_content"
android:layout_height="wrap_content">
<!-- Original layout here -->
</ScrollView>
</LinearLayout>
Of course, if you just put only one layout inside the scrollview, there is no need for the outer layout:
<?xml version="1.0" encoding="utf-8"?>
<ScrollView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
xmlns:android="http://schemas.android.com/apk/res/android">
<!-- Original layout here -->
</ScrollView>
My main xml layout file....
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/relLayoutPlayerActivity"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#drawable/backgroundimage"
android:orientation="vertical" >
</LinearLayout>
I created the viewpager.....
that layout file......
<?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:orientation="vertical" >
<android.support.v4.view.ViewPager
android:id="#+id/carousel_layout_home"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_gravity="center"
android:overScrollMode="never" />
</LinearLayout>
I load the images into this view pager by creating three classes & another xml file......
now I want to add this viewpager into linearlayout of main xml file....
It means I want dynamically view the viewpager in mainxml file. how to that? pls give me answer
thankyou
If you have two Layouts such as LinearLayout you can add one onto the other with addView(). In your Activity it would look something along the lines of,
LinearLayout layout = (LinearLayout) findViewById(R.id.relLayoutPlayerActivity);
LayoutInflater inflater = (LayoutInflater) this.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
layout.addView(inflater.inflate(R.layout.idOfLayoutHoldingYourViewPager, null));
I included second layout to first layout like this:
<?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="match_parent" >
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="300dp"
android:layout_height="match_parent"
android:layout_gravity="clip_horizontal"
android:layout_alignParentLeft="true"
android:id="#+id/rlMenu"
>
<Button
android:id="#+id/bMusteriler"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="Musteriler"
android:textSize="45dp"
android:layout_alignParentLeft="true"
/>
</RelativeLayout>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="match_parent"
android:layout_toRightOf="#id/rlEkranlar"
>
<include
android:id="#+id/include1"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
layout="#layout/ikinci" />
</RelativeLayout>
</RelativeLayout>
Problem is how can I change included layout when clicked a button(on java code)?
I suggest ViewFlipper inside RelativeLayout of your include statements. Try like this:
<ViewFlipper xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/vf"
android:layout_width="fill_parent"
android:layout_height="wrap_content" >
<include android:id="#+id/include1" layout="#layout/ikinci" />
<include android:id="#+id/map" layout="#layout/third_layout" />
</ViewFlipper>
Access ViewFlipper as below.
Initially first layout is output:
ViewFlipper vf = (ViewFlipper)findViewById(R.id.vf);
For Button onClickListener:
button.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
vf.setDisplayedChild(1);
}
});
There is two ways to change layouts in code:
A. Change visibility. Include tow different layouts in your xml:
<include
android:id="#+id/id1"
android:visibility="visible"/>
<include
android:id="#+id/id2"
android:visibility="gone"/>
and in code use this:
findViewById(R.id.id1).setVisibility(View.GONE);
findViewById(R.id.id2).setVisibility(View.VISIBLE);
B. Manually add children. Use the same xml as you use now and add in code you can add or delete children:
yourRelativeLayout.removeAllViews();
yourRelativeLayout.addView(viewToInclude);
Offtopic:
You don't need to write xmlns:android param in RelativeLayout. Just for the most top tag in layout file.
Have you tried to get the instance of the current view of the xml you have included the other xml and use findViewById(). View v is the first layout and against this view you use .findViewById()