I ended up writing my own class, expanding ScrollView
Since you are asking ... here is the code. Probably not the cleanest, but it does what I want.
Note that it expects layout_weight to be set when the view is created, and you donβt have to set weigthSum in the parent LinearLayout or you will get funny things (since the weight of this changes from the original value to 0 depending on the size of the contents of the ScrollView)
First, in a layout file, a view is declared as follows:
<com.matthieu.widget.ShrinkingScrollView android:id="@+id/scroll" android:scrollbars="vertical" android:layout_height="0dp" android:layout_width="fill_parent" android:layout_weight="4" android:background="#cc0000" > <TextView android:id="@+id/in_scroll_view" android:layout_height="wrap_content" android:layout_width="fill_parent" android:background="#0000bb" /> </com.matthieu.widget.ShrinkingScrollView>
Then the widget code:
import android.content.Context; import android.util.AttributeSet; import android.widget.LinearLayout; import android.widget.ScrollView; public class ShrinkingScrollView extends ScrollView { private float original_weight=-1; public ShrinkingScrollView(Context context) { super(context); } public ShrinkingScrollView(Context context, AttributeSet attrs) { super(context, attrs); } public ShrinkingScrollView(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); } @Override protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { LinearLayout.LayoutParams params = (LinearLayout.LayoutParams) getLayoutParams(); float previous_weight = params.weight; if (original_weight == -1) original_weight = params.weight; if ((getChildCount()>0) && (getVisibility()!=GONE)) { super.onMeasure(widthMeasureSpec, MeasureSpec.makeMeasureSpec(0,MeasureSpec.UNSPECIFIED)); int overall_height = getChildAt(0).getMeasuredHeight(); super.onMeasure(widthMeasureSpec, heightMeasureSpec); if (getMeasuredHeight() >= overall_height) { if (previous_weight != 0) { params.weight=0; params.height = overall_height; setLayoutParams(params); post(new Runnable() { public void run() { requestLayout(); } }); } setMeasuredDimension(getMeasuredWidth(),overall_height); } else if (previous_weight == 0) { params.weight = original_weight; params.height = 0; setLayoutParams(params); post(new Runnable() { public void run() { requestLayout(); } }); } } else { super.onMeasure(widthMeasureSpec, heightMeasureSpec); } } }
source share