通缉:TableLayout-Like ListView

时间:2011-04-01 05:28:49

标签: android user-interface listview android-layout

我的问题可能是,“如何使用两个单行非包装TextView创建单行水平LinearLayout,其中左TextView始终占据可用屏幕宽度的1/3,右TextView始终占用2 / 3可用的屏幕宽度,当文本标签太长而无法显示时,文本标签将被截断?“ (如果这个问题足够清楚,读者 - 那就是你 - 已经考虑过他们愿意分享的解决方案,那么进一步阅读问题和问题描述可能是不必要的。)

使用四个此类LinearLayouts填充的ListView将如下所示:

medium length text ---- short text
short text         ---- text that is too loooooooooooooo...
loooooooooooooo... ---- short text
loooooooooooooo... ---- text that is too loooooooooooooo...
在此模型中,第一行中的 ,左右文本标签足够短以完全显示,在第二行,左侧标签足够短以完全显示,而右侧标签的文字太长并因此被截断,并且文本的开头右侧标签与第一行的右侧文本垂直对齐,在视觉上创建一个列,就好像它在TableLayout中一样,在第三行中,左侧标签的文本太长并且是截断,以便与第二行和第一行的左侧文本垂直对齐,右侧标签的文本开始与第二行和第一行的右侧文本垂直对齐,和第四行 ,左边标签的文字太长,因此显示类似于第三行的左文本,右边的文字显示bel太长了,因此与第二行的右侧文本类似地显示。

在stackoverflow和其他地方的各个帖子中,我认为虽然使用带有ArrayAdapter的TableLayout有点可能,但是有一些缺点,并且它可能不是正确的方法。

我当然尝试了很多布局参数组合,但目标还没有达到目的。我试图找出一个适用于许多不同屏幕尺寸的解决方案,因此指定特定的像素宽度可能不会很好。

也许以下简单的代码示例(带有屏幕截图)是解决方案的一个很好的起点,只需要一些小的修改。

(stackoverflow代码格式化程序对此代码感到不满。所以,请原谅任何时髦的格式。)

public class TableLayoutLikeListView extends ListActivity
{
  @Override
  public void onCreate(Bundle savedInstanceState)
  {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.list);

    List<Datum> data = new ArrayList<Datum>();
    data.add(new Datum("short", "short"));
    data.add(new Datum("short", "loooooooooooooooooooooooooooooooooooooooooonnnnnnnnnnnnnnnnnnnnnng"));
    data.add(new Datum("loooooooooooooooooooooooooooooooooooooooooonnnnnnnnnnnnnnnnnnnnnng", "short"));
    data.add(new Datum("loooooooooooooooooooooooooooooooooooooooooonnnnnnnnnnnnnnnnnnnnnng",
        "loooooooooooooooooooooooooooooooooooooooooonnnnnnnnnnnnnnnnnnnnnng"));
    setListAdapter(new MyAdapter(this, R.layout.row, data));
  }
}
class Datum
{
  String left, right;

  Datum(String left, String right)
  {
    this.left = left;
    this.right = right;
  }
}

class MyAdapter extends ArrayAdapter<Datum>
{
  List<Datum> data;
  int textViewResourceId;

  MyAdapter(Context context, int textViewResourceId, List<Datum> data)
  {
    super(context, textViewResourceId, data);
    this.data = data;
    this.textViewResourceId = textViewResourceId;
  }

  @Override
  public View getView(int position, View convertView, ViewGroup parent)
  {
    if (convertView == null)
    {
      LayoutInflater inflater = (LayoutInflater) getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
      convertView = inflater.inflate(textViewResourceId, null);
    }
    Datum datum = data.get(position);
    if (datum != null)
    {
      TextView leftView = (TextView) convertView.findViewById(R.id.left);
      TextView rightView = (TextView) convertView.findViewById(R.id.right);
      if (leftView != null)
      {
        leftView.setText(datum.left);
      }
      if (rightView != null)
      {
        rightView.setText(datum.right);
      }
    }
    return convertView;
  }
}

list.xml: 
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content">
    <ListView
        android:id="@+id/android:list"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content" />
</LinearLayout>
row.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="horizontal"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:weightSum="3">
    <TextView
        android:id="@+id/left"
        android:layout_width="0dip"
        android:layout_height="wrap_content"
        android:layout_weight="1"
        android:singleLine="true" />
    <TextView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="----" />
    <TextView
        android:id="@+id/right"
        android:layout_width="0dip"
        android:layout_height="wrap_content"
        android:layout_weight="2"
        android:singleLine="true" />
</LinearLayout>

(注意虽然TextView确实有ellipsize属性,但似乎没有必要改变,因为将singleLine设置为true会截断并椭圆化标签。我可能错了。)

以下是此代码的屏幕截图:

任何建议当然都值得赞赏。

4 个答案:

答案 0 :(得分:6)

我认为本教程会对您有所帮助。试试this ..

您的row.xml应如下所示:

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="wrap_content"
android:gravity="left|center"
android:layout_width="wrap_content"
android:paddingBottom="10px"
android:paddingTop="10px"
android:paddingLeft="3px">
 <TextView
    android:id="@+id/TextView01"
    android:layout_width="70dip"
    android:layout_height="wrap_content"
    android:gravity="left"
    android:singleLine="true"
    android:textSize="15dip"
    android:textStyle="bold"
    android:textColor="#d08021"
    android:paddingLeft="20dip">
 </TextView>
 <TextView

    android:id="@+id/TextView02"
    android:layout_width="200dip"
    android:layout_height="wrap_content"
    android:gravity="left"
    android:singleLine="true"
    android:layout_marginLeft="10dip"
    android:textSize="15dip"
    android:textStyle="bold"
    android:textColor="#7f0000">
 </TextView>

</LinearLayout>

你需要这种类型的布局吗?如果我没有错,请纠正我。 See the output when i tried the above layout file.

答案 1 :(得分:3)

您可以使用TableLayout并使其表现得像ListView(至少在视觉上)。 Here is我的回答。

答案 2 :(得分:3)

hackbod提出了另一个好看的论点,为什么ListViews无法在问题Does Android have a Table like Adapter for ListView的答案中布置像TableViews这样的行。

答案 3 :(得分:2)

我能想到的最好的方法是让row.xml看起来像这样。它并不理想,但它会保持行具有固定的宽度,这将按尺寸的变化进行缩放,但不会基于文本。它将为您提供80%的表格布局,并具有ListView的优势。

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_height="wrap_content"
android:gravity="left|center"
android:layout_width="wrap_content"
android:paddingBottom="10px"
android:paddingTop="10px"
android:paddingLeft="3px">
 <TextView
    android:id="@+id/TextView01"
    android:layout_width="0dp"
    android:layout_weight=1
    android:layout_height="wrap_content"
    android:gravity="left"
    android:singleLine="true"
    android:textSize="15dip"
    android:textStyle="bold"
    android:textColor="#d08021"
    android:paddingLeft="20dip">
 </TextView>
 <TextView

    android:id="@+id/TextView02"
    android:layout_width="0dp"
    android:layout_weight=3
    android:layout_height="wrap_content"
    android:gravity="left"
    android:singleLine="true"
    android:layout_marginLeft="10dip"
    android:textSize="15dip"
    android:textStyle="bold"
    android:textColor="#7f0000">
 </TextView>

</LinearLayout>