我创建了一个简单的应用程序来说明在 SDK 17 和 SDK 18 之间包装在 RelativeLayout 中时 LinearLayout 的行为方式的变化。首先,屏幕截图:
当 targetSdkVersion 为“17”时:
当 targetSdkVersion 为“18”时:
此活动的布局是:
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#00ffff"
android:orientation="vertical" >
<include layout="@layout/test_list_item"/>
<ListView
android:id="@+id/listview"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:overScrollMode="never"
android:scrollingCache="false" >
</ListView>
</LinearLayout>
text_list_item.xml 是:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#ff0000" >
<TextView
android:id="@+id/text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerInParent="true"
android:background="#ffff00"
android:padding="10dp"
android:text="foobar"
android:textColor="#000000" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_alignBottom="@id/text"
android:layout_alignTop="@id/text"
android:background="#00ff00"
android:orientation="horizontal"
android:weightSum="1.0" >
<View
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="0.5"
android:background="#0000ff" />
</LinearLayout>
</RelativeLayout>
活动的 onCreate() 如下所示:
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_test);
findViewById(R.id.text).bringToFront();
final ListView mListView = (ListView) findViewById(R.id.listview);
mListView.setAdapter(new TestAdapter());
}
TestAdapter 看起来像这样:
public class TestAdapter extends BaseAdapter {
private static final int COUNT = 3;
@Override
public int getCount() {
return COUNT;
}
@Override
public Object getItem(int position) {
return null;
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public boolean areAllItemsEnabled() {
return true;
}
@Override
public boolean isEnabled(int position) {
return false;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
final View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.test_list_item, null);
view.findViewById(R.id.text).bringToFront();
return view;
}
当 target = 17 时,LinearLayout 的子视图在位于 ListView 内部和在 ListView 外部时都被正确调整为可用宽度的 50%。当 target = 18 用作列表项的布局时,它不会调整大小。在这种情况下,它的宽度保持在“0dp”并且永远不会调整大小。
理想情况下,我希望以 SDK 19 为目标。不过,为了做到这一点,我以某种方式适应这种行为变化。关于如何实现的任何想法?
顺便说一句,布局如此复杂和“怪异”是有原因的;我意识到有更直接的方法可以实现这种特殊的视觉效果。
编辑:
提供更多关于我为什么使用这种病态布局的信息:它用于“仪表”。LinearLayout 中的 View 使用 ScaleAnimation 进行拉伸或收缩,使其占据总可用宽度的所需百分比。棘手的是我需要在仪表顶部覆盖文本,并且我希望仪表的高度由文本确定。
因此,外部的 RelativeLayout 应该“与其父级一样宽”,但只能“与其包含的 TextView 一样高”。该 RelativeLayout 内部的 LinearLayout 应该与其父级一样宽和高。LinearLayout 中的 View 应该和包含它的 LinearLayout 一样高,但只有一半宽。
这正是我在针对 SDK 17和/或在 SDK 18+ 中当布局不用作 ListView item 的内容时得到的行为。
编辑
发布到开发者群:
https://groups.google.com/forum/#!msg/android-developers/KuoY5Tklyms/TbNq6ndD_PwJ