在一些项目中,比如搜索,广告热门关键词等等都会用到下面这种效果的排版,如下图:
其实最通用的实现方案是自定义一个ViewGroup,然后自己计算布局。但是这种方式对于一些对自定义控件不太熟悉的人来说,有些难度,这里有一个通过拼凑的方法实现这种效果,下面是源代码,偷懒了一下,不想封装了,直接就写在一个Activity里面,谁有需要,自己去优化:
import android.app.Activity;
import android.graphics.Paint;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.ViewGroup;
import android.view.ViewGroup.LayoutParams;
import android.widget.LinearLayout;
import android.widget.TextView;
public class TextViewItemActivity extends Activity {
private boolean isFristTime = true;
/** 标签之间的间距 px */
final int itemMargins = 50;
/** 标签的行间距 px */
final int lineMargins = 50;
private ViewGroup container = null;
private String[] tags = { "大约在冬季", "漂洋过海的来看你", "天下有情人", "我很认真", "夜夜夜夜", "想你的夜", "背叛", "趁早", "旧情绵绵", "谁明浪子心", "安妮",
"说谎的爱人", "不浪漫的罪名", "不愿一个人", "风吹麦浪" };
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.textview_layout);
container = (ViewGroup) findViewById(R.id.container);
}
@Override
public void onWindowFocusChanged(boolean hasFocus) {
super.onWindowFocusChanged(hasFocus);
if (hasFocus && isFristTime) {
isFristTime = false;
final int containerWidth = container.getMeasuredWidth() - container.getPaddingRight()
- container.getPaddingLeft();
final LayoutInflater inflater = getLayoutInflater();
/** 用来测量字符的宽度 */
final Paint paint = new Paint();
final TextView textView = (TextView) inflater.inflate(R.layout.item_textview, null);
final int itemPadding = textView.getCompoundPaddingLeft() + textView.getCompoundPaddingRight();
final LinearLayout.LayoutParams tvParams = new LinearLayout.LayoutParams(LayoutParams.WRAP_CONTENT,
LayoutParams.WRAP_CONTENT);
tvParams.setMargins(0, 0, itemMargins, 0);
paint.setTextSize(textView.getTextSize());
LinearLayout layout = new LinearLayout(this);
layout.setLayoutParams(new LinearLayout.LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT));
layout.setOrientation(LinearLayout.HORIZONTAL);
container.addView(layout);
final LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(LayoutParams.MATCH_PARENT,
LayoutParams.WRAP_CONTENT);
params.setMargins(0, lineMargins, 0, 0);
/** 一行剩下的空间 **/
int remainWidth = containerWidth;
for (int i = 0; i < tags.length; ++i) {
final String text = tags[i];
final float itemWidth = paint.measureText(text) + itemPadding;
if (remainWidth > itemWidth) {
addItemView(inflater, layout, tvParams, text);
} else {
resetTextViewMarginsRight(layout);
layout = new LinearLayout(this);
layout.setLayoutParams(params);
layout.setOrientation(LinearLayout.HORIZONTAL);
/** 将前面那一个textview加入新的一行 */
addItemView(inflater, layout, tvParams, text);
container.addView(layout);
remainWidth = containerWidth;
}
remainWidth = (int) (remainWidth - itemWidth + 0.5f) - itemMargins;
}
resetTextViewMarginsRight(layout);
}
}
/***************** 将每行最后一个textview的MarginsRight去掉 *********************************/
private void resetTextViewMarginsRight(ViewGroup viewGroup) {
final TextView tempTextView = (TextView) viewGroup.getChildAt(viewGroup.getChildCount() - 1);
tempTextView
.setLayoutParams(new LinearLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT));
}
private void addItemView(LayoutInflater inflater, ViewGroup viewGroup, LayoutParams params, String text) {
final TextView tvItem = (TextView) inflater.inflate(R.layout.item_textview, null);
tvItem.setText(text);
viewGroup.addView(tvItem, params);
}
}Activity的Layout文件
<?xml version="1.0" encoding="utf-8"?>
<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_width="match_parent"
android:layout_height="wrap_content"
android:background="@android:color/darker_gray"
android:gravity="center_horizontal"
android:paddingBottom="5dp"
android:paddingLeft="10dp"
android:paddingRight="10dp"
android:paddingTop="5dp"
android:text="这只是一个demo而已"
android:textSize="16sp" >
</TextView>
<LinearLayout
android:id="@+id/container"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="50dp"
android:background="#8864dd"
android:orientation="vertical"
android:paddingBottom="10dp"
android:paddingLeft="10dp"
android:paddingRight="10dp"
android:paddingTop="10dp" >
</LinearLayout>
</LinearLayout>TextView的Layout文件:
<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="@android:color/darker_gray"
android:paddingBottom="10dp"
android:paddingLeft="10dp"
android:paddingRight="10dp"
android:paddingTop="10dp"
android:text="测试的"
android:textSize="16sp" >
</TextView>嗯,就这样,谁需要用到的就用,其实好像网上有一个开源的控件,我忘记叫啥名字了,自己去找找。
本文介绍了在Android中使用LinearLayout和TextView实现标签项自动换行的解决方案,适用于搜索、广告热门关键词等场景。通过示例代码展示了一种不依赖自定义ViewGroup的简单方法。
2256

被折叠的 条评论
为什么被折叠?



