Keep ScrollView from taking up too much height - android

I am trying to keep the ScrollView from taking too much space at the bottom of the screen as it keeps my two buttons from showing. I also don't want to manually set a height for the ScrollView.
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical">
<LinearLayout
...
android:orientation="horizontal">
<Button .../>
<TextView .../>
<Button .../>
</LinearLayout>
<ScrollView
android:layout_width="math_parent"
android:layout_height="wrap_content">
<ImageView .../>
<ImageView .../>
<ImageView .../>
</ScrollView>
<LinearLayout
...
android:orientation="horizontal">
<Button .../>
<Button .../>
</LinearLayout>
</LinearLayout>
This is a generalized version of my layout. What is happening is that the ScrollView extends all the way to the bottom of the screen no matter how many items are in it. This causes the two buttons at the bottom of the screen to not be visible.
How can I stop this from happening without manually setting a height for the ScrollView?
I've used android:layout_height="wrap_content" for all my views.
Isn't this supposed to automatically distribute the height of the views to fit the screen's height?
(Wanted to include images, but my rep isn't high enough yet (-_-))

The way I would resolve this today is by using RelativeLayout as a base. Anchor the two LinearLayout's to the top and bottom of the RelLayout respectively. Then I would insert the ScrollView but I would make sure to set it's layout properties as follows:
android:layout_below="topLinearLayout"
android:layout_above="bottomLinearLayout"

Have you tried using layout_weight for the ScrollView. IIRC, if a non-zero weight is set for ONE element (and the corresponding dimension set to 0dp) then it'll fill up the remaining space in that dimension, after setting out the measurements for sibling views (in this case, the LinearLayout on top and bottom of the ScrollView.
Apologies, not got an Android environment to check and it's been a while.
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<LinearLayout>
...
Something at the top
...
</LinearLayout>
<ScrollView
android:layout_width="match_parent"
**android:layout_height="0dp"
android:layout_weight="1"**>
<ImageView .../>
<ImageView .../>
<ImageView .../>
</ScrollView>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal" >
...
buttons
...
</LinearLayout>
</LinearLayout>
Here's an answer with more information about the layout_weight attribute.

Related

Trying to size correctly android layouts

I'm struggling on a layout management so I decided to ask here.
I would like to get 3 layouts working in a certain way.
I have 3 views vertically dispatched into a RelativeLayout (let's call them VTop, VMiddle and VBottom).
VBottom is a Button, I want him to stay aligned with the bottom of the screen and to never move or get resized (actually working).
VMiddle is a scroll view. I want this ScrollView to take all possible place between the bottom button (VBottom) and the top most layout (VTop) but never having it height inferior to an specific size.
I would like to have VTop (A linear layout containing some TextViews and other stuffs) wrapping all of its content as long as VMiddle doesn't get smaller that its minimum size.
Actually the code I have is almost working but when I Inflate too much content into VMiddle, it keeps growing towards the top of the screen and VTop completely disappear. I want VMiddle to stay at it minimum size if VTop doesn't have enough space to wrap his content.
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/relativeLayout1">
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="#+id/linearLayout1" <!-- VTop -->
android:layout_above="#+id/eventDetail_RateLayout"
android:layout_alignParentTop="true"
android:layout_margin="10sp"> <!-- LOT OF VIEWS, NEED TO BE WRAPPED AS MUCH AS POSSIBLE -->
</LinearLayout>
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="100px"
android:id="#+id/eventDetail_RateLayout" <!-- Not visible for now, you can ignore it -->
android:layout_marginTop="10dp"
android:layout_marginBottom="10dp"
android:minWidth="25px"
android:minHeight="25px"
android:background="#color/common_google_signin_btn_text_light_default"
android:layout_above="#+id/eventDetail_CommentScrollView"
android:visibility="gone" />
<ScrollView
android:id="#+id/eventDetail_CommentScrollView" <!-- VMiddle -->
android:background="#4D4A58"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_above="#+id/eventDetail_commentButton">
<LinearLayout
android:orientation="vertical"
android:minWidth="25px"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="#+id/eventDetail_CommentLayout" />
</ScrollView>
<Button
android:text="commenter"
android:id="#+id/eventDetail_commentButton" <!-- VMiddle, this one is doing ok -->
android:background="#666"
android:textColor="#f8f8f8"
android:layout_width="match_parent"
android:layout_height="30sp"
android:layout_alignParentBottom="true" />
</RelativeLayout>
Thanks for your answers.
Try the following code for the ScrollView -
<ScrollView
android:id="#+id/eventDetail_CommentScrollView" <!-- VMiddle -->
android:background="#4D4A58"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_below="#id/linearLayout1"
android:layout_weight="1"
android:layout_above="#+id/eventDetail_commentButton">
...
</ScrollView>
Use this, however the kind of UI you want can be easily achieved using Linear layout and using weight and weightSum properties.. also rename ID of the layout and views accordingly
<?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/topLayout"
android:layout_width="match_parent"
android:layout_height="100dp"
android:layout_alignParentTop="true"
android:background="#70AD47"
android:orientation="vertical">
</LinearLayout>
<ScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_above="#+id/btnBottom"
android:layout_below="#+id/topLayout"
android:background="#ED7D31"
android:minHeight="400dp">
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical">
</LinearLayout>
</ScrollView>
<Button
android:id="#+id/btnBottom"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:background="#4472C4"
android:text="Bottom button" />
</RelativeLayout>
1. Add attribute android:layout_below="#id/linearLayout1" and android:layout_above="#id/eventDetail_commentButton" to ScrollView to keep it at middle position.
2. Use ScrollView and its child LinearLayout height android:layout_width="match_parent" although its not necessary.
No matter how big the top and bottom layout, middle scrollview will always fill the middle free spaces. It will never change the height of top and bottom layout.
Here is the working layout:
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/relativeLayout1">
<LinearLayout
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="#+id/linearLayout1"
android:layout_alignParentTop="true"
android:layout_margin="10sp">
</LinearLayout>
<Button
android:text="commenter"
android:id="#+id/eventDetail_commentButton"
android:background="#666"
android:textColor="#f8f8f8"
android:layout_width="match_parent"
android:layout_height="30sp"
android:layout_alignParentBottom="true" />
<ScrollView
android:id="#+id/eventDetail_CommentScrollView"
android:background="#4D4A58"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_below="#id/linearLayout1"
android:layout_above="#id/eventDetail_commentButton">
<LinearLayout
android:orientation="vertical"
android:minWidth="25px"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/eventDetail_CommentLayout" />
</ScrollView>
</RelativeLayout>
Hope this will help~
Use android:layout_below="#+id/linearlayout1"
in eventDetail_RateLayout
I'm pretty sure none of the given answers achieve what you're looking for. What you wanna do is not simple because it involves a circular dependency: you basically want your vTop view to wrap and fill any space left by your vMiddle view (android:layout_above="#id/vMiddle") and at the same time you want your vMiddle view to wrap and fill any space left by your vTop view (android:layout_below="#id/vTop").
The only solution I can imagine would be to check and set the view sizes programmatically, I don't think this is doable only by rearranging your layout.
I finally achieved to get something close to what I wanted. I combined layout_above and below and fixed the size of VTop by making the Huge TextView scrollable. I have now VTop and VBottom at a fixed size and VMiddle taking the rest of the place at the center.
Thanks for your fast answers :)

ScrollView goes on top of another layout Android

In the following code I've got two main containers, a RelativeLayout and a ScrollView. I need the RelativeLayout to be on top fixed and below that I need the ScrollView with Images to be scrollable. I've got the following two questions:
Though my ScrollView is scrollable but it goes on top of the RelativeLayout. !important
The view of my images present within the vertical LinearLayout are thumbnail sized. If I have 15-20 images, they take a lot of vertical space. How do I have the images to fit the maximum in a row based on the screen size and then go to the next row?
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
</LinearLayout>
</RelativeLayout>
<ScrollView
android:layout_width="fill_parent"
android:layout_height="wrap_content">
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="vertical">
<ImageView>
</ImageView>
<ImageView>
</ImageView>
<ImageView>
</ImageView>
<ImageView>
</ImageView>
</LinearLayout>
</ScrollView>
Follow these in simple way:
You need to use a fixed height for the parent, i.e., <RelativeLayout>.
Set the height of the ScrollView to match_parent.
Make sure you put everything inside a LinearLayout.
Finally you would end up with this:
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
</RelativeLayout>
</LinearLayout>
First, you can set your RelativeLayout's height to a fixed value. Then set your ScrollView's height to match_parent, so it takes up all the available space. Then both of these should be contained in a vertical LinearLayout, to avoid any overlapping.

What am I misunderstanding about aligning views at the bottom?

I tried to align my linearlayout at the bottom of my entire layout which is relative, and found the solution here that does it: How to align views at the bottom of the screen?
But why wouldn't this work also?
<RelativeLayout 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"
tools:context="com.sandbox.activities.ListActivity">
<ListView
android:id="#+id/my_listview"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<LinearLayout
android:id="#+id/search_footer"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="#id/my_listview"
android:orientation="horizontal"
android:layout_alignParentBottom="true">
<EditText
android:id="#+id/my_edittext"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:hint="Enter Search Term" />
<Button
android:id="#+id/find_button"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="Find"
android:onClick="findThings"/>
</LinearLayout>
If the listview turns out to be short, like 1 row, "search_footer" is just underneath it, and there is a huge gap below it.
1) "search_footer" is told to align at the bottom of the parent, which is the relativelayout. Since the relativelayout's height is match_parent, and it's the root layout, this means the whole height of the screen, so why wouldn't "search_footer" be at the bottom of the screen no matter the size of the listview?
2) Also, if I change the search_footer's height to match_parent, I expected a really tall button, but it remained unchanged-why?
Add to ListView this attribute
android:layout_above="#id/search_footer"
and remove
android:layout_below="#id/my_listview"
attribute from LinearLayout.
You specified that search_footer align to bottom of parent but also to be below the listview, so in the case that the list is short the search footer just stretches in the space between the listview and the bottom of the screen. you want to specify the footer to be aligned to the bottom of the parent and the listview to be above it:
<ListView
android:id="#+id/my_listview"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_above="#+id/search_footer"
/>
<LinearLayout
android:id="#+id/search_footer"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
android:layout_alignParentBottom="true">
When you change the height of the search_footer the buttons doe't change because they are set to android:layout_height="wrap_content". Your layout would normally change when you do this however in this case it didn't change either, due to the same reason as above

Layout_weight to get 2 equal height layouts

I'm currently modifying an xml layout, and I want to group all of the views into 2 sections, each half of the height available. The layout looks something like this:
<LinearLayout
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
>
...Lots of stuff...
</LinearLayout>
What I've done is to wrap each "half" of the views in a linear layout, and assign a weight to each.
<LinearLayout
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
>
<!-- Top half -->
<LinearLayout
android:layout_weight="1"
android:layout_height="0dp"
android:layout_width="fill_parent"
android:orientation="vertical">
... stuff and things ...
</LinearLayout>
<!-- Bottom half -->
<LinearLayout
android:layout_weight="1"
android:layout_height="0dp"
android:layout_width="fill_parent"
android:orientation="vertical">
... things and stuff ...
</LinearLayout>
</LinearLayout>
I can't figure out why this doesn't give me 2 equal panes. The lower one seems to take up 90% of the available space. I've tried adding (android:weightSum="2") to the container layout, but to no avail. None of these layouts have IDs, so the code behind shouldn't be able to modify them. Any idea what is going on here? Are the child views able to modify their "half" containers so that they wouldn't appear equal?
This link may be of some use to you:
http://www.chess-ix.com/blog/the-use-of-layout_weight-with-android-layouts/
What you are doing seem to be correct, but probably the content in your Linearlayouts may be the culprit.
Trying adding a weightSum to the parent LinearLayout, like so:
<LinearLayout
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:weightSum="2">
<!-- Top half -->
<LinearLayout
android:layout_weight="1"
android:layout_height="0dp"
android:layout_width="match_parent"
android:orientation="vertical">
... stuff and things ...
</LinearLayout>
<!-- Bottom half -->
<LinearLayout
android:layout_weight="1"
android:layout_height="0dp"
android:layout_width="match_parent"
android:orientation="vertical">
... things and stuff ...
</LinearLayout>
</LinearLayout>
Also, I change layout_height of the children: you won't need fill_parent for the child LinearLayouts since the parent has that property already.

Equal button height for RelativeLayout (while still filling up all space)

I have an Android application that goes about like this:
<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:orientation="vertical">
<RelativeLayout
android:id="#+id/toplayout"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="0.90" >
<Button
android:id="#+id/button_1_of_10"
android:layout_width="70dip"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true"
android:text="#string/text_0x1701" />
<Button
android:id="#+id/button_2_of_10"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignRight="#+id/button_1_of_10"
android:layout_below="#+id/button_1_of_10"/>
<!--Another 8 buttons-->
<RelativeLayout
android:id="#+id/contentpane"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:layout_toRightOf="#+id/button_1_of_10" >
</RelativeLayout>
</RelativeLayout>
<RelativeLayout
android:id="#+id/actionbuttonslayout"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="0.10">
</RelativeLayout>
</LinearLayout>
I need the 10 buttons to fill up the entire height from the top to the footer (the 0.1 weighted RelativeLayout), while all the buttons keep an equal height. However, I want to know whether there is a kind of equivalent to the layout_weight from LinearLayout, but for RelativeLayouts, as it's not performant to have nested weights in LinearLayouts. I'm not really looking for other solutions, because I still have some thing to try, but I want to know whether or not this is possible?
My question, just to be clear, is: Is it possible to have an amount of Buttons with an equal height in a RelativeLayout and at the same time fill up all the available space?
To use weight you need to use a LinearLayout, just make a linear layout with the buttons take the space you want and then on each button inside have android:layout_height="0dp" and also a android:layout_weight="1"
You don't need to sum all the weights to 1, just think of items with the same weight have the same size

Categories

Resources