流式布局SearchFlowLayout

来源:互联网 发布:淘宝开店货从哪里来 编辑:程序博客网 时间:2024/06/06 03:54

看到搜索框下面一般都有最近的搜索记录,这些搜索记录一般是流式布局,下面的是一个流式布局,一个继承ViewGroup的自定义view,其中一种使用场景就是在搜索框下面,效果图如下:


下面是SearchFlowLayout的源码:

public class SearchFlowLayout extends ViewGroup {    List<Line> lines = new ArrayList<Line>();//所有的行    private Line currentLine;    public SearchFlowLayout(Context context) {        super(context);    }    public SearchFlowLayout(Context context, AttributeSet attrs) {        super(context, attrs);    }    public SearchFlowLayout(Context context, AttributeSet attrs, int defStyleAttr) {        super(context, attrs, defStyleAttr);    }    private OnItemClickListener mListener;    public void setOnItemClickListener(OnItemClickListener listener) {        this.mListener = listener;    }    public interface OnItemClickListener {        void click(int position);    }    @Override    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {        lines.clear();        currentLine = null;        int width = MeasureSpec.getSize(widthMeasureSpec);        float maxWidth = width - getPaddingLeft() - getPaddingRight();        float horizontalDistance = dp2px(getContext(), 10);        float vercitalDistance = dp2px(getContext(), 10);        int childCount = getChildCount();        currentLine = new Line(maxWidth, horizontalDistance, vercitalDistance);        lines.add(currentLine);        for (int i = 0; i < childCount; i++) {            View childView = getChildAt(i);            final int position = i;            childView.setOnClickListener(new OnClickListener() {                @Override                public void onClick(View v) {                    if (mListener != null) {                        mListener.click(position);                    }                }            });            measureChild(childView, widthMeasureSpec, heightMeasureSpec);            if (currentLine.canAddView(childView)) {                currentLine.addView(childView);            } else {                currentLine = new Line(maxWidth, horizontalDistance, vercitalDistance);                if (currentLine.canAddView(childView)) {                    currentLine.addView(childView);                }                lines.add(currentLine);            }        }        int hight = 0;        for (int i = 0; i < lines.size(); i++) {            if (i == 0) {                hight += getPaddingTop();            } else if (i == lines.size() - 1) {                hight += getPaddingBottom();            }            hight += lines.get(i).mLineHight + vercitalDistance;        }        setMeasuredDimension(width, hight);    }    @Override    protected void onLayout(boolean changed, int l, int t, int r, int b) {        int lineTop = getPaddingTop();        for (int i = 0; i < lines.size(); i++) {            Line line = lines.get(i);            line.layout(lineTop);            lineTop += line.mLineHight + line.mVercitalDistance;        }    }    /**     * 每一行     */    class Line {        public List<View> mViews = new ArrayList<View>();        public float mHorizontalDistance;//行中两个子View之间水平间距        public float mVercitalDistance;//两个行竖直间距        public float mMaxWidth;//行中的最大的宽度        public float mUseWidth;//行中已经使用的宽度        public float mLineHight;//行的高度        public Line(float maxWidth, float horizontalDistance, float vercitalDistance) {            this.mMaxWidth = maxWidth;            this.mHorizontalDistance = horizontalDistance;            this.mVercitalDistance = vercitalDistance;        }        /**         * 是否能添加View         *         * @param view         * @return         */        private boolean canAddView(View view) {            if (mViews.size() == 0) {                mUseWidth += getPaddingLeft() + getPaddingRight() + view.getMeasuredWidth();                return true;            } else {                mUseWidth += view.getMeasuredWidth() + mHorizontalDistance;            }            if (mUseWidth <= mMaxWidth) {                return true;            }            return false;        }        /**         * 添加View         *         * @param view         */        private void addView(View view) {            mViews.add(view);            mLineHight = mLineHight < view.getMeasuredHeight() ? view.getMeasuredHeight() : mLineHight;        }        /**         * 摆放子view         */        private void layout(int lineTop) {            int left = getPaddingLeft();            int top = lineTop;            int right = 0;            int bottom = 0;            for (int i = 0; i < mViews.size(); i++) {                View view = mViews.get(i);                right = left + view.getMeasuredWidth();                bottom = top + view.getMeasuredHeight();                view.layout(left, top, right, bottom);                left += view.getMeasuredWidth() + mHorizontalDistance;            }        }    }    /**     * dp转px     *     * @param context     * @param dp     * @return     */    public int dp2px(Context context, float dp) {        float density = context.getResources().getDisplayMetrics().density;        int px = (int) (dp * density + 0.5f);        return px;    }}

使用:

xml布局:

<?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">    <FrameLayout        android:layout_width="match_parent"        android:layout_height="wrap_content"        android:paddingTop="10dp"        android:paddingBottom="10dp"        android:background="#E6E6E6">        <LinearLayout            android:layout_width="match_parent"            android:layout_height="45dp"            android:orientation="horizontal"            android:background="@drawable/search_bg"            android:layout_marginLeft="10dp"           android:layout_marginRight="10dp">            <ImageView                android:layout_width="40dp"                android:layout_height="40dp"                android:layout_marginLeft="10dp"                android:layout_gravity="center_vertical"                android:background="@drawable/search1"/>            <EditText                android:layout_width="match_parent"                android:layout_height="match_parent"                android:background="@null"                />        </LinearLayout>    </FrameLayout>    <com.org.sleepgod.widget.SearchFlowLayout        android:id="@+id/fl_view"        android:padding="10dp"        android:layout_width="match_parent"        android:layout_height="wrap_content">    </com.org.sleepgod.widget.SearchFlowLayout></LinearLayout>

java代码:

public class FlowLayoutActivity extends Activity {    private SearchFlowLayout mSearchFlowLayout;    private String[] mNames = new String[]{"大主宰","龙王传说","一念永恒","雪鹰领主","帝霸","最强狂兵","美食供应商","我是大明星","全职法师","我的贴身校花","重生完美时代"    ,"318女生宿舍"};    @Override    protected void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.activity_flowlayout);        mSearchFlowLayout = (SearchFlowLayout) findViewById(R.id.fl_view);        for (int i = 0; i < mNames.length; i++) {            TextView textView = new TextView(this);            textView.setText(mNames[i]);            textView.setBackgroundResource(R.drawable.text_bg);            GradientDrawable gradientDrawable = (GradientDrawable) textView.getBackground();            gradientDrawable.setStroke(1, UIUtils.randomColor());            mSearchFlowLayout.addView(textView);        }        mSearchFlowLayout.setOnItemClickListener(new SearchFlowLayout.OnItemClickListener() {            @Override            public void click(int position) {                Toast.makeText(FlowLayoutActivity.this,mNames[position],Toast.LENGTH_SHORT).show();            }        });    }}

text_bg

<?xml version="1.0" encoding="utf-8"?><shape xmlns:android="http://schemas.android.com/apk/res/android">    <solid android:color="#FFFFFF" />    <stroke        android:width="1dp"        android:color="#61e0fe" />    <padding        android:bottom="6dp"        android:left="10dp"        android:right="10dp"        android:top="6dp" />    <corners android:radius="25dp" /></shape>

search_bg

<?xml version="1.0" encoding="utf-8"?><shape xmlns:android="http://schemas.android.com/apk/res/android">    <corners android:radius="25dp"/>    <solid android:color="#FFF"/>    <stroke android:color="#7A7A7A"></stroke></shape>


源码链接:https://github.com/sleepgodMaster/sleepgod-master/blob/master/src/main/java/com/org/sleepgod/widget/SearchFlowLayout.java




0 0
原创粉丝点击