In my Android app I've created a vertical layout to hold a horizontal list of images (thumbnails) over top a larger view of a selected image from the list. For some reason I cannot get the horizontal list to display horizontally it only appears as a vertical list.
<LinearLayout
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="15">
<LinearLayout
android:orientation="horizontal"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_weight="1">
<Mvx.MvxListView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
local:MvxBind="ItemsSource Images"
local:MvxItemTemplate="#layout/image_item" />
</LinearLayout>
<ImageView
android:src="#drawable/BDSeal"
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:layout_margin="10.0dp"
android:id="#+id/imageView1" />
</LinearLayout>
In Android, the system ListViews are vertical only.
There are open source horizontal list views available - eg cheesebaron once provided http://blog.ostebaronen.dk/2012/12/horizontal-listview-for-mono-for-android.html - and I think this has been updated more recently.
Also some people use the PageAdapter to show this type of horizontally scrolling list.
Related
I have built the following XML layout:
<?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:background="#color/white"
android:orientation="vertical" >
<LinearLayout
android:id="#+id/ll1"
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="0.2"
android:orientation="horizontal" >
<ImageView
android:id="#+id/imageView1"
android:layout_width="0dp"
android:layout_height="fill_parent"
android:layout_weight="0.3"
android:gravity="center"
android:src="#drawable/logo" />
<TextView
android:layout_width="0dp"
android:layout_height="fill_parent"
android:layout_weight="0.7"
android:gravity="center"
android:text="#string/my_profile"
android:textColor="#A669DA"
android:textSize="20sp" />
</LinearLayout>
<LinearLayout
android:id="#+id/ll2"
android:background="#A669DA"
android:layout_marginTop="10dp"
android:layout_marginBottom="10dp"
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="0.15"
android:orientation="horizontal" >
<TextView
android:id="#+id/TextView"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_marginLeft="10dp"
android:layout_marginTop="20dp"
android:text="#string/payroll_header"
android:textColor="#FFFFFF"
android:textSize="20sp" />
</LinearLayout>
<ScrollView
android:id="#+id/scrollView1"
android:layout_width="fill_parent"
android:layout_height="0dp"
android:layout_weight="0.65" >
<LinearLayout
android:id="#+id/ll3"
android:layout_width="fill_parent"
android:layout_height="0dp"
android:orientation="vertical"
android:weightSum="2" >
<ExpandableListView
android:id="#+id/expandableListView1"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:fadeScrollbars="true" >
</ExpandableListView>
<HorizontalScrollView
android:id="#+id/horizontalScrollView1"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
<ExpandableListView
android:id="#+id/expandableListView2"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
</ExpandableListView>
</HorizontalScrollView>
<ListView
android:id="#+id/listView1"
android:layout_width="match_parent"
android:layout_height="wrap_content" >
</ListView>
</LinearLayout>
</ScrollView>
</LinearLayout>
The root element of this XML layout is a linear layout. It contains 2 linear layouts and one scroll. Since scroll view can only have one child, it contains a linear layout which in turn contains an expandable listView, horizontal scrollview (which contains an expandable listview) and a listview. As you can see, this is a very complicated layout, and I think it should be possible to simplify. Basically, I want the top 2 linear layouts to always take 35% of the screen, and the scrollview to take the rest. That's why I gave a weight of 0.2 to the first linear layout, 0.15 to the second linear layout, and 0.65 to scrollView.
Within the scrollView, I would like each of the 3 elements to take as much space as they would need, so that user scrolls down if he/she doesn't see everything. I know that expandableListView and ListView are already scrollable, so I will disable scrolling in them, so that parent's scroll bar is used.
However, I am facing several problems with this design:
1) In the first screenshot, you can see an expandableListView, horizontalScrollBar (with an expandableListView), and a listView.
Each of them has height set to "wrap content", so I would expect each of them to take as much space as they need. However, you can see in the second screenshot that when I open the second expandable listView (the one within a horizontal scrollBar), listview doesn't move down to make space for the expanded list view. How can I achieve it, so that each of them moves down when the expandable list above expands? Is the only way to do it is to combine them all in one expandableListView?
2) My second expandableListView is in the horizontalScrollBar, however, I can't scroll it horizontally. Can I even put horizontal scrollBar inside a vertical scrollBar?
First off, a little simplification: Your second LinearLayout (the 0.15 one) can be left out since it only has a single child. Just be sure to adjust the layout parameters of that single child (the TextView).
For your problem #1, try calling invalidate() or requestLayout() on your root view.
Problem #2 is actually solved: Link
My general impression is that this nesting of ScrollViews and ListViews is pretty complex. Have you considered alternatives such as TabLayout or DrawerLayout?
Cheers
Please help me in this code below :(
I am working on a grid view which should show 4 fixed number of rows in landscape mode. It should display data from an arraylist and should scroll horizontally. I used normal grid view and rotated it by 270. Then inside the grid cell I have used a single Text View which I had to rotate by 90 in order to show the text straight. I set the numColumns property to 4. So the expected is to show 4 rows with data from the arraylist. But I am not getting the grid cell displaying text properky in 4 rows. I am pasting the below xml code for gridview and the single customized xml containing the textview which is inside the gridcell. I tried changing all the properties of the grid view, scroll view and text view. But dont know whats wrong with this code.
<ScrollView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_below="#id/textView_installed_app" >
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_gravity="top"
android:orientation="vertical" >
<GridView
android:id="#+id/gridView"
android:layout_width="wrap_content"
android:layout_height="400dp"
android:columnWidth="10dp"
android:gravity="center"
android:numColumns="4"
android:rotation="270" >
</GridView>
</LinearLayout>
</ScrollView>
Customized TextView inside gridview cell:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<TextView
android:layout_gravity="center_vertical|center_horizontal"
android:layout_marginRight="10dp"
android:id="#+id/textview_gridcell"
android:layout_width="wrap_content"
android:layout_height="150dp"
android:rotation="90"
/>
i am developing an android app where i am showing day wise channel schedule (multiple rows).
now in this i have to provide both vertical and horizontal scrollability.
vertical scrollability will be normal , but horizontal scrollability should be synchronized
that is when user scrolls horizontally all other rows should also be scrolled in a sync.
i tried using table layout but its not going good with my requirement and i have also tried TwoWayView but i am not able to sync the horizontal scrolling.
i would like to know i anyone have faced/solved the similar situation.
Any leads on this is highly appreciated.
xml for vertical and horizontal Scrolling :-
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:id="#+id/vertical_scroll_view2">
<HorizontalScrollView
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:id="#+id/horizontal_scroll_view2">
<LinearLayout
android:layout_height="wrap_content"
android:layout_width="910dp"
android:id="#+id/scheduleContainer"
android:orientation="vertical"
/>
</HorizontalScrollView>
</ScrollView>
.....
xml for TwoWayView:-
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="wrap_content">
<TextView
android:id="#+id/weekday"
android:layout_height="fill_parent"
android:layout_width="40dp"
android:textSize="12dp"
android:textStyle="bold" />
<com.mobiotics.tvb_stb.utilityclasses.TwoWayView
xmlns:tools="http://schemas.android.com/tools"
android:id="#+id/hlist"
style="#style/TwoWayView"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_toRightOf="#id/weekday"
android:scrollbars="none"
android:drawSelectorOnTop="false"
tools:context="com.mobiotics.tvb_stb.activity.HomeScreenActivity" />
</RelativeLayout>
i am adding twoway list to linear layout .
If you can have a ListView, I would start there. Just drop the ListView into a HorizontalScrollView. Make sure to set the width of the HorizontalScrollView to wrap_content. I noticed you have it set to fill_parent.
I have applied scroll view to the entire layout and that layout has one listview. when running the application in the emulator both scroll views are working one scroll view for entire layout and another scroll view for listview (both works fine). but when i installed my app in the phone only outer scroll view is working scroll view for listview is not working. Can any one please tell me the reason and solution for my problem.
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/ScrollView1"
android:layout_width="fill_parent"
android:layout_height="fill_parent">
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="#drawable/bg4"
android:orientation="vertical"
android:scrollbarAlwaysDrawVerticalTrack="true" >
<ListView
android:id="#+id/listViewTickets"
android:layout_width="match_parent"
android:layout_height="200dp"
android:layout_gravity="center_horizontal"
android:layout_marginTop="10dp" >
</ListView>
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="right"
android:layout_marginBottom="70dp"
android:orientation="horizontal"
>
<Button
android:id="#+id/btnNew"
android:layout_width="80dp"
android:layout_height="30dp"
android:background="#drawable/btnnew" />
<Button
android:id="#+id/btnUpdate"
android:layout_width="80dp"
android:layout_height="30dp"
android:layout_marginLeft="10dp"
android:layout_marginRight="10dp"
android:background="#drawable/edit" />
</LinearLayout>
The content of list view is displayed dynamically.
I have found the youtube video Google I/O 2010 - The world of ListView an essential watch. In it it's mentioned to never use multiple scrolling widgets unless they scroll on a different axis.
A list view is already scrollable so you can't add it to a scroll view.
Here's a similar question and an answer from the Google engineer in charge of the ListView:
How can I put a ListView into a ScrollView without it collapsing?
I'm struggling to get a layout looking correctly, and I've tried to produce the shortest, smallest possible example of my problem.
My goal is to have a header and footer View, at the top and bottom of the screen, with a ListView in between the two, with another View (let's call it the label, it's the gray box from the screen shots) directly below the ListView. This label, and the footer should always be shown when ListView needs to scroll.
Visual Result
When the ListView does not need to scroll (this is correct):
When the ListView needs to scroll, the footer and the gray box are pushed off screen (wrong):
Layout
<?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">
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="header"
android:padding="20dp"
android:textSize="18sp"
android:background="#color/red"/>
<ListView android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="#android:id/list" />
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="this should be directly below the ListView, but not pushed off screen when the ListView needs to scroll"
android:padding="5dp"
android:background="#color/light_gray"
android:textColor="#color/black"/>
<!-- Used to push the footer to the bottom -->
<View android:layout_width="0dp" android:layout_height="0dp" android:layout_weight="1"/>
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="footer"
android:padding="20dp"
android:textSize="18sp"
android:background="#color/blue"/>
</LinearLayout>
Test Activity
public class TestActivity extends ListActivity
{
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
ArrayList<String> items = new ArrayList<String>();
items.add("one");
items.add("two");
items.add("three");
items.add("four");
items.add("five");
items.add("six");
items.add("seven");
items.add("eight");
items.add("nine");
items.add("ten");
setListAdapter(new ArrayAdapter<String>(this, R.layout.simple_list_item_1, items));
setContentView(com.myproject.android.R.layout.test);
}
}
I've tried a few different approaches, such as giving the ListView layout_weight="1" and removing the blank View that I use to push the footer to the bottom. This is almost what I want, it keeps the footer and label visible when the ListView scrolls, but when it only has 1 or 2 items, I need the gray box right below the ListView. I've also attempted to use a RelativeLayout, without success. I guess I'm completely misunderstanding things.
EDIT
Here's my attempt with a RelativeLayout which still isn't correct.
<?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">
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="header"
android:padding="20dp"
android:textSize="18sp"
android:background="#color/red"
android:id="#+id/header"
/>
<ListView android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="#android:id/list"
android:layout_below="#id/header"/>
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="this should be directly below the ListView, but not pushed off screen when the ListView needs to scroll"
android:padding="5dp"
android:background="#color/light_gray"
android:textColor="#color/black"
android:layout_below="#android:id/list"/>
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="footer"
android:padding="20dp"
android:textSize="18sp"
android:background="#color/blue"
android:layout_alignParentBottom="true"
android:id="#+id/footer"/>
</RelativeLayout>
Relative Layout (Still Wrong):
Add android:layout_weight="1" to the listview. That will make it the biggest element in the LinearLayout, without pushing the other ones off the screen.
This layout adds the header a top of the screen and the footter and the bottom. The list fills the rest of the screen. With theses aproach list elements never be obscured by the footer. See how to add the gray box below the XML...
<?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">
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="header"
android:padding="20dp"
android:textSize="18sp"
android:background="#color/red"
android:id="#+id/header"
/>
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="footer"
android:padding="20dp"
android:textSize="18sp"
android:background="#color/blue"
android:layout_alignParentBottom="true"
android:id="#+id/footer"/>
<ListView android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:id="#android:id/list"
android:layout_below="#id/header"
android:layout_above="#id/footer"/>
</RelativeLayout>
Ok. This XML solves the problem of the missing footer. Now we have to add a gray box at the end of the list. I think there is two ways to do it:
Use the addFooterView method: http://developer.android.com/reference/android/widget/ListView.html#addFooterView(android.view.View)
Play with the adapter and the getViewTypeCount() method so you can define two types or elements: normal elements and footer element. http://developer.android.com/reference/android/widget/BaseAdapter.html#getViewTypeCount()
A solution that worked for me was to add positive padding to the bottom of the list view and negative padding to the top of the "footer". This will work in a linear layout or a relative layout.
<ListView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:paddingBottom="50dp"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="-50dp"/>
Two years late to answer the question, but I will leave my solution so it may help someone with the same problem. I solve this problem using 2 nested LinearLayouts and using layout_weigth. Maybe not the best performatic layout, but it reaches the desired effect.
You need to arrange your layout this way:
Your ListView will have wrap_content height to take only the needed space when not filling the entire screen.
Your ListView will be inside a layout with height using layout_weight so the list will take only the needed space when not filling the entire screen and to take only a limited space of the screen when it have size enouth to push the views out of screen.
The grey box view the should be immediately below the list will have wrap_content height and will be a sinbling of the layout of step 2.
This layout and the grey box will be inside a second layout with wrap_content height so they can stay together.
Now you have a layout with the list and the grey view and the list won't push the other views out of screen if it gets too big; you only need to move the footer view to the bottom of the screen.
5a. If you are using RelativeLayout as your root layout, you can do as sgallego said and use android:layout_alignParentBottom.
5b. But if you are using LinearLayout you need to create a third layout with layout_weigth and put inside the layout of step 4 and a empty view also with layout_weigth to fill the empty space.
Here is a commented example.
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<!-- Header -->
<TextView
android:id="#+id/RecordStudy_StudyLabel"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="#string/RecordStudy_StudyLabel"
android:textSize="#dimen/text_large" />
<!-- Body -->
<LinearLayout
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:orientation="vertical" >
<!--
This layout encapsules the list and the button that must be immediately
below the list with a wrap_content height, so the list plus the button
fills only as much space as they need (if the list is not big enouth to
fill the entire screen).
-->
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical" >
<!--
Layout with varaible size with a list inside.
Using layout_weight tells android that this layout should not grow
greater then the screen, but uses only the free space.
-->
<LinearLayout
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:orientation="vertical" >
<!--
Inside this limited height layout, there is a list with height
wrap_content so it can grow as much as it needs INSIDE the
layout (through scrolling).
-->
<ListView
android:id="#+id/RecordStudy_StudyList"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</LinearLayout>
<!-- Button immediately below the list -->
<Button
android:id="#+id/RecordStudy_AddStudy"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="#string/RecordStudy_AddStudy" />
</LinearLayout>
<!-- Space between the list and the footer -->
<View
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1" />
</LinearLayout>
<!-- Footer -->
<Button
android:id="#+id/RecordStudy_ConfirmButton"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="#string/RecordStudy_ConfirmButton" />
</LinearLayout>
One solution that I implemented and found useful was to keep the listview inside a linear layout with fixed height so that it doesn't extend and overlap other items.
Something like this:
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="header"
android:padding="20dp"
android:textSize="18sp"
android:background="#color/red"
android:id="#+id/header"
/>
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="150dip" //assume 150dip height is sufficient
<ListView android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="#android:id/list"
android:layout_below="#id/header"/>
</LinearLayout>
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:text="this should be directly below the ListView, but not pushed off screen when the ListView needs to scroll"
android:padding="5dp"
android:background="#color/light_gray"
android:textColor="#color/black"
android:layout_below="#android:id/list"/>