前言
flow layout, 流式佈局, 這個概念在移動端或者前端開發中很常見,想淘寶,京東都有,之前公司項目有用到一個流佈局顯示關鍵詞並動態添加的效果,於是科補並實現了一下。
展示
因爲軟鍵盤的問題,本來是想上靜態圖的,但是強迫症上來了,還是搞了個動態圖,就是有點失真,抱歉抱歉,另外求推薦一款截屏軟件啊!!!
裏面寫死了是textview、當然有需求的小夥伴們可以自己改一下,比較簡單。
分析
我們來看看他需要些什麼,不難看出
1. 左右間距,行間距
2. 子view的點擊事件,長按事件
3. 點擊的同事判斷是否是最後一個添加按鈕,
4. 計算每個子view的高度,取最高的,
5. 計算每個子view的寬度,疊加超過控件寬度則需要換行
6. 點擊事件的回調,1:點擊添加按鈕的回調,2:點擊其他按鈕的回調返回當前選中的list字符串集合,便於通知服務器
7. 長按事件點擊確定刪除標籤的回調,便於通知服務器
接下來就只是上代碼了,因爲你們搬磚我也是個初窺,所以註釋比較全,就不多做解釋了
XCFlowLayout.java
public class XCFlowLayout extends ViewGroup implements View.OnClickListener, View.OnLongClickListener {
/**
* 存儲所有子View,每行每行的儲存
*/
private ArrayList<ArrayList<View>> mAllChildViews = new ArrayList<>();
/**
* 存儲所有選擇的子View,
*/
private ArrayList<View> BackViews = new ArrayList<>();
/**
* 存儲所有選擇的item,
*/
private ArrayList<String> Backitem = new ArrayList<>();
/**
* 記錄每個子view的選中情況
*/
private Map<String, Boolean> MapBack = new HashMap<>();
/**
* 孩子的數量,複製
*/
public ArrayList<String> listChild;
/**
* 每一個孩子的左右的間距 默認值 12,單位是px
*/
int mHSpace = 12;
/**
* 每一行的上下的間距
*/
int mVSpace = 16;
/**
* 每一行的高度
*/
private ArrayList<Integer> mLineHeight = new ArrayList<>();
/**
* 嵌套 ScrollView 的子view的高度,重新計算的
*/
public int viewHeight = 0;
/**
* 用來計算子View佔據的高度
*/
public int childHeight;
private MarginLayoutParams lp;
private Context context;
private boolean isCheck;
private addViewListener OnaddListener;
// 顯示隱藏鍵盤用的
InputMethodManager m;
public XCFlowLayout(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public XCFlowLayout(Context context) {
this(context, null);
}
public XCFlowLayout(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.XCFlowLayout, defStyleAttr, 0);
//獲取橫縱向的間距
mHSpace = a.getDimensionPixelSize(R.styleable.XCFlowLayout_h_space, dpToPx(6));
mVSpace = a.getDimensionPixelSize(R.styleable.XCFlowLayout_v_space, dpToPx(8));
}
/**
* 設置間距
* @param hSpace
*/
public void setHSpace(int hSpace) {
this.mHSpace = hSpace;
}
/**
* 設置上下間距
* @param vSpace
*/
public void setVSpace(int vSpace) {
this.mVSpace = vSpace;
}
public void setAddView(addViewListener OnaddListener) {
this.OnaddListener = OnaddListener;
}
@SuppressWarnings("ResourceType")
public void setChildView(ArrayList<String> listChild, Context context) {
this.listChild = listChild;
this.context = context;
lp = new MarginLayoutParams(
LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
lp.leftMargin = mHSpace/2;
lp.rightMargin = mHSpace/2;
lp.topMargin = mVSpace/2;
lp.bottomMargin = mVSpace/2;
for (int i = 0; i < listChild.size(); i++) {
TextView view = new TextView(context);
view.setText(listChild.get(i));
view.setTextColor(Color.WHITE);
view.setTag(listChild.get(i));//當做點擊事件用
view.setBackgroundDrawable(getResources().getDrawable(
R.drawable.textview_bg));
view.setLayoutParams(lp);
addView(view);
view.setOnClickListener(this);
view.setOnLongClickListener(this);
MapBack.put(view.getTag().toString(), false);
}
TextView view = new TextView(context);
view.setText(UiUtils.getString(R.string.addView));
view.setTextColor(Color.GREEN);
view.setTag(UiUtils.getString(R.string.addView));//當做點擊事件用
view.setBackgroundDrawable(getResources().getDrawable(R.drawable.textview_bg));
view.setLayoutParams(lp);
addView(view);
view.setOnClickListener(this);
// 實例化顯示隱藏鍵盤用的,當前顯示則隱藏,當前隱藏則顯示
m = (InputMethodManager) context.getSystemService(Context.INPUT_METHOD_SERVICE);
}
public void setChildView(String[] listChild, Context context) {
for (int i = 0; i < listChild.length; i++) {
this.listChild.add(listChild[i]);
}
setChildView(this.listChild, context);
}
public void addView(String str) {
TextView view = new TextView(context);
view.setText(str);
view.setTextColor(Color.WHITE);
view.setTag(str);//當做點擊事件用
view.setBackgroundDrawable(getResources().getDrawable(R.drawable.textview_bg));
view.setLayoutParams(lp);
addView(view, listChild.size());
view.setOnClickListener(this);
view.setOnLongClickListener(this);
MapBack.put(view.getTag().toString(), false);
listChild.add(listChild.size(), str);
}
private void OnremoveView(View v,String tag) {
removeView(v);
MapBack.remove(tag);
listChild.remove(tag);
if (OnaddListener!=null)
OnaddListener.Onremove(tag);
}
@Override
public void onClick(View v) {
if (v.getTag() != null) {
String id = v.getTag().toString();
if (id.equals(UiUtils.getString(R.string.addView))) {
// 點擊添加按鈕的代碼
// 顯示隱藏鍵盤用的,當前顯示則隱藏,當前隱藏則顯示
m.toggleSoftInput(0, InputMethodManager.HIDE_NOT_ALWAYS);
// 點擊添加按鈕的代碼
if (OnaddListener != null) {
// 獲取焦點
// 顯示光標、
OnaddListener.addView();
}
} else {
setBackground(v,id);
}
}
}
@Override
public boolean onLongClick(View v) {
final String id = v.getTag().toString();
if (!id.equals(UiUtils.getString(R.string.addView))) {
ShowDialog(v.getContext(), v,id);
}
return true;
// setOnLongClickListener中return的值決定是否在長按後再加一個短按動作
// true爲不加短按,false爲加入短按
}
/**
* 因爲我們自定義view對於屬性爲wrap_content這種情況,如果不做處理其實是與match_parent是一樣效果的。
*
* @param widthMeasureSpec
* @param heightMeasureSpec 拿到父容器推薦的寬和高以及計算模式
*/
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
super.onMeasure(widthMeasureSpec, heightMeasureSpec);
int sizeWidth = MeasureSpec.getSize(widthMeasureSpec);
int sizeHeight = MeasureSpec.getSize(heightMeasureSpec);
int measureWidthMode = MeasureSpec.getMode(widthMeasureSpec);
int measureHeightMode = MeasureSpec.getMode(heightMeasureSpec);
//根據自身的寬度約束子控件寬度,測量孩子的大小 計算模式
//measureChildren(widthMeasureSpec, heightMeasureSpec);
int width = 0;// 自己測量的 寬度
int height = 0;// 自己測量的高度
// 記錄每一行的寬度和高度
int lineWidth = 0;
int lineHeight = 0;
// 獲取子view的個數
int childCount = getChildCount();
for (int i = 0; i < childCount; i++) {
View child = getChildAt(i);
// 測量子View的寬和高
measureChild(child, widthMeasureSpec, heightMeasureSpec);
// 得到LayoutParams
MarginLayoutParams lp = (MarginLayoutParams) child.getLayoutParams();
// 子View佔據的寬度
int childWidth = child.getMeasuredWidth() + lp.leftMargin
+ lp.rightMargin;
// 子View佔據的高度
int childHeight = child.getMeasuredHeight() + lp.topMargin
+ lp.bottomMargin;
// 換行時候 當前行寬加即將添加的行寬小於(=)父控件行寬時,即不換行
if (lineWidth + childWidth < sizeWidth) {
// 疊加行寬
lineWidth += childWidth;
// 得到最大行高
lineHeight = Math.max(lineHeight, childHeight);
} else {//換行情況
// 對比得到最大的寬度
width = Math.max(width, lineWidth);
// 開始新的一行行寬即是childWidth
lineWidth = childWidth;
// 記錄行高
height += lineHeight;
// 開始新的一行行高即是childHeight
lineHeight = childHeight;
}
}
//漏掉了最後一行未加
height += lineHeight;
setMeasuredDimension((measureWidthMode == MeasureSpec.EXACTLY) ? sizeWidth : width, (measureHeightMode == MeasureSpec.EXACTLY) ? sizeHeight : height + 10);
}
@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
mAllChildViews.clear();
mLineHeight.clear();
// 獲取當前ViewGroup的寬度
int width = getWidth();
int lineWidth = 0;//行寬
int lineHeight = 0;//行高
// 記錄當前行的view
ArrayList<View> lineViews = new ArrayList<>();
int childCount = getChildCount();
for (int i = 0; i < childCount; i++) {
View child = getChildAt(i);
MarginLayoutParams lp = (MarginLayoutParams) child
.getLayoutParams();
int childWidth = child.getMeasuredWidth();
int childHeight = child.getMeasuredHeight();
// 如果需要換行,當前計算的寬加上即將加上的寬和間距
if (childWidth + lineWidth + lp.leftMargin + lp.rightMargin > width) {
// 記錄LineHeight
mLineHeight.add(lineHeight);
// 記錄當前行的Views
mAllChildViews.add(lineViews);
// 重置行的寬高
lineWidth = 0;
lineHeight = childHeight + lp.topMargin + lp.bottomMargin;
// 重置view的集合
lineViews = new ArrayList();
}
lineWidth += childWidth + lp.leftMargin + lp.rightMargin;
lineHeight = Math.max(lineHeight, childHeight + lp.topMargin
+ lp.bottomMargin);
lineViews.add(child);
}
// 處理最後一行
mLineHeight.add(lineHeight);
mAllChildViews.add(lineViews);
// 設置子View的位置
int left = 0;
int top = 0;
// 獲取行數
int lineCount = mAllChildViews.size();
for (int i = 0; i < lineCount; i++) {
// 當前行的views和高度
lineViews = mAllChildViews.get(i);
lineHeight = mLineHeight.get(i);
for (int j = 0; j < lineViews.size(); j++) {
View child = lineViews.get(j);
// 判斷是否顯示
if (child.getVisibility() == View.GONE) {
continue;
}
MarginLayoutParams lp = (MarginLayoutParams) child
.getLayoutParams();
int cLeft = left + lp.leftMargin;
int cTop = top + lp.topMargin;
int cRight = cLeft + child.getMeasuredWidth();
int cBottom = cTop + child.getMeasuredHeight();
// 進行子View進行佈局
child.layout(cLeft, cTop, cRight, cBottom);
left += child.getMeasuredWidth() + lp.leftMargin
+ lp.rightMargin;
}
left = 0;
top += lineHeight;
}
}
/**
* 與當前ViewGroup對應的LayoutParams
*/
@Override
public LayoutParams generateLayoutParams(AttributeSet attrs) {
return new MarginLayoutParams(getContext(), attrs);
}
private void setBackground(View v,String tag) {
//根據tag看是否
if (!MapBack.get(tag)) {
BackViews.add(v);
Backitem.add(tag);
MapBack.put(tag, true);
v.setBackgroundDrawable(getResources().getDrawable(R.drawable.textview_bg02));
} else {
BackViews.remove(v);
Backitem.remove(tag);
MapBack.put(tag, false);
v.setBackgroundDrawable(getResources().getDrawable(R.drawable.textview_bg));
}
if (OnaddListener!=null)
OnaddListener.BackTag(Backitem);
}
private void ShowDialog(final Context context, final View v,final String tag) {
BaseDialog.Builder customBuilder = new
BaseDialog.Builder(context)
.setTitle("確定刪除")
.setMessage("點擊確定即刪除該排除條件,確定刪除?")
.setNegativeButton("取消", new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
})
.setPositiveButton("確定",
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int which) {
OnremoveView(v,tag);
dialog.dismiss();
}
}).setImage(-1);
BaseDialog dialog = null;
if (dialog == null) {
dialog = customBuilder.create();
}
dialog.show();
}
/**
* dp的單位轉換爲px的
*
* @param dps
* @return
*/
private int dpToPx(int dps) {
return Math.round(getResources().getDisplayMetrics().density * dps);
}
public interface addViewListener {
/**
* 點擊添加按鈕,彈出佈局添加的
*/
void addView();
/**
* 返回選中的list字符串集合
*/
void BackTag(ArrayList<String> list);
/**
* 點擊刪除的,返回點擊的當前字符串
*/
void Onremove(String tag);
}
}
註釋全在代碼中了,提一下,這裏區分點擊事件用的的是settag的方法。還有就是ShowDialog方法是之前博客裏面封裝的一個自定義彈出框,
下面的是xml
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:clipToPadding="true"
android:fillViewport="true"
android:fitsSystemWindows="true" >
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<include
android:id="@+id/title_bar"
layout="@layout/header_titlebar" />
<RelativeLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
<ScrollView
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:background="#ffffff" >
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:orientation="vertical" >
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginTop="12dp"
android:orientation="horizontal"
android:paddingLeft="10dp"
android:paddingRight="8dp" >
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:singleLine="true"
android:text="國內排除條件"
android:textColor="#000000"
android:textSize="25sp"
android:textStyle="bold" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:orientation="horizontal" >
<TextView
android:id="@+id/anmyte_Select"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginRight="8dp"
android:background="@drawable/custom_viewgroup_qx"
android:text="全選"
android:textSize="16sp" />
<TextView
android:id="@+id/anmyte_Open"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="@drawable/custom_viewgroup_zk"
android:text="展開"
android:textSize="16sp" />
</LinearLayout>
</LinearLayout>
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="6dp"
android:layout_marginRight="8dp"
android:layout_marginTop="4dp"
android:background="#E3E3E3" />
<RadioButton
android:id="@+id/anmyte_you_xiang"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="15dp"
android:layout_marginTop="8dp"
android:text="郵箱"
android:textColor="#000000"
android:textSize="20sp"
android:checked="false" />
<!-- ====== -->
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginBottom="8dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3" />
<com.topeasychian_fengs.widgets.XCFlowLayout
android:id="@+id/flowlayout"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:visibility="gone" >
</com.topeasychian_fengs.widgets.XCFlowLayout>
<TextView
android:id="@+id/amyying_c_x"
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3"
android:visibility="gone" />
<!-- ====== -->
<RadioButton
android:id="@+id/anmyte_dian_hua"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="15dp"
android:layout_marginTop="8dp"
android:text="電話"
android:textColor="#000000"
android:textSize="20sp" />
<!-- ====== -->
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginBottom="8dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3" />
<com.topeasychian_fengs.widgets.XCFlowLayout
android:id="@+id/flowlayout_2"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:visibility="gone" >
</com.topeasychian_fengs.widgets.XCFlowLayout>
<TextView
android:id="@+id/amyying_c_x_2"
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3"
android:visibility="gone" />
<!-- ====== -->
<RadioButton
android:id="@+id/anmyte_B2B"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="15dp"
android:layout_marginTop="8dp"
android:text="B2B平臺"
android:textColor="#000000"
android:textSize="20sp" />
<!-- ====== -->
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginBottom="8dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3" />
<com.topeasychian_fengs.widgets.XCFlowLayout
android:id="@+id/flowlayout_3"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:visibility="gone" >
</com.topeasychian_fengs.widgets.XCFlowLayout>
<TextView
android:id="@+id/amyying_c_x_3"
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3"
android:visibility="gone" />
<!-- ====== -->
<RadioButton
android:id="@+id/anmyte_B2C"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="15dp"
android:layout_marginTop="8dp"
android:text="B2C平臺"
android:textColor="#000000"
android:textSize="20sp" />
<!-- ====== -->
<!-- ====== -->
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginBottom="8dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3" />
<com.topeasychian_fengs.widgets.XCFlowLayout
android:id="@+id/flowlayout_4"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:visibility="gone" >
</com.topeasychian_fengs.widgets.XCFlowLayout>
<TextView
android:id="@+id/amyying_c_x_4"
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3"
android:visibility="gone" />
<!-- ====== -->
<!-- ================== -->
<LinearLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginTop="25dp"
android:orientation="horizontal"
android:paddingLeft="10dp"
android:paddingRight="8dp" >
<TextView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="國外排除條件"
android:textColor="#000000"
android:textSize="25sp"
android:textStyle="bold" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:orientation="horizontal" >
<TextView
android:id="@+id/awmyte_Select"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginRight="8dp"
android:background="@drawable/custom_viewgroup_qx"
android:text="全選"
android:textSize="16sp" />
<TextView
android:id="@+id/awmyte_Open"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="@drawable/custom_viewgroup_zk"
android:text="展開"
android:textSize="16sp" />
</LinearLayout>
</LinearLayout>
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="6dp"
android:layout_marginRight="8dp"
android:layout_marginTop="4dp"
android:background="#E3E3E3" />
<RadioButton
android:id="@+id/awmyte_you_xiang"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="15dp"
android:layout_marginTop="8dp"
android:text="郵箱"
android:textColor="#000000"
android:textSize="20sp" />
<!-- ====== -->
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginBottom="8dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3" />
<com.topeasychian_fengs.widgets.XCFlowLayout
android:id="@+id/flowlayout_5"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:visibility="gone" >
</com.topeasychian_fengs.widgets.XCFlowLayout>
<TextView
android:id="@+id/amyying_c_x_5"
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3"
android:visibility="gone" />
<!-- ====== -->
<RadioButton
android:id="@+id/awmyte_dian_hua"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="15dp"
android:layout_marginTop="8dp"
android:text="電話"
android:textColor="#000000"
android:textSize="20sp" />
<!-- ====== -->
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginBottom="8dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3" />
<com.topeasychian_fengs.widgets.XCFlowLayout
android:id="@+id/flowlayout_6"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:visibility="gone" >
</com.topeasychian_fengs.widgets.XCFlowLayout>
<TextView
android:id="@+id/amyying_c_x_6"
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3"
android:visibility="gone" />
<!-- ====== -->
<RadioButton
android:id="@+id/awmyte_B2B"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="15dp"
android:layout_marginTop="8dp"
android:text="B2B平臺"
android:textColor="#000000"
android:textSize="20sp" />
<!-- ====== -->
<TextView
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginBottom="8dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3" />
<com.topeasychian_fengs.widgets.XCFlowLayout
android:id="@+id/flowlayout_7"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:visibility="gone" >
</com.topeasychian_fengs.widgets.XCFlowLayout>
<TextView
android:id="@+id/amyying_c_x_7"
android:layout_width="fill_parent"
android:layout_height="0.5dp"
android:layout_marginLeft="15dp"
android:layout_marginRight="15dp"
android:background="#E3E3E3"
android:visibility="gone" />
<!-- ====== -->
<Button
android:id="@+id/amybtn_tijiao"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_marginLeft="30dp"
android:layout_marginRight="30dp"
android:layout_marginTop="40dp"
android:text="提 交" />
</LinearLayout>
</ScrollView>
<LinearLayout
android:id="@+id/amylin_fa_song"
android:layout_width="fill_parent"
android:layout_height="40dp"
android:layout_alignParentBottom="true"
android:layout_marginBottom="3dp"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:orientation="horizontal"
android:visibility="gone" >
<EditText
android:id="@+id/amyEdit_tian_jia"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:layout_marginRight="8dp"
android:layout_weight="1"
android:background="@drawable/details_set_a"
android:gravity="center_vertical"
android:paddingLeft="8dp"
android:textCursorDrawable="@drawable/color_cursor" />
<!-- android:textCursorDrawable="@drawable/color_cursor" -->
<!-- 光標顏色 -->
<TextView
android:id="@+id/amyText_tian_jia"
android:layout_width="wrap_content"
android:layout_height="fill_parent"
android:background="@drawable/collection_bg02"
android:gravity="center"
android:text="添加" />
</LinearLayout>
</RelativeLayout>
</LinearLayout>
</RelativeLayout>
自定義屬性
<declare-styleable name="XCFlowLayout">
<!--橫縱向的間距-->
<attr name="h_space" format="dimension" />
<attr name="v_space" format="dimension" />
</declare-styleable>
到這裏代碼段就結束了
忘記activity裏面的代碼了我去
XCFlowLayoutActivity.java
public class XCFlowLayoutActivity extends MyBaseActivity implements OnLayoutChangeListener {
@BindView(R.id.mXCFlowLayout)
XCFlowLayout mXCFlowLayout;
ArrayList<String> list;
ArrayList<String> BackList;
@BindView(R.id.edit_01)
EditText edit01;
@BindView(R.id.lin_01)
LinearLayout lin01;
@BindView(R.id.tv_01)
TextView tv01;
@BindView(R.id.title)
TextView title;
// 屏幕高度
private int screenHeight = 0;
// 軟件盤彈起後所佔高度閥值
private int keyHeight = 0;
InputMethodManager m;
@Override
protected void onCreate() {
initView();
}
@Override
protected int getLayout() {
return R.layout.activity_xcflowlayout;
}
private void initView() {
title.setText("XCFlowLayout");
list = new ArrayList<>();
list.add("asdasdas");
list.add("sdasdsa");
list.add("ghfghfgg");
list.add("ghjkhjkh");
list.add("lioiioui");
list.add("weqbnmjk");
list.add("ikhnghn");
list.add("yterwwe");
list.add("olpszaq");
list.add("aqvgju");
list.add("rgyswdr");
list.add("qxbhuil");
BackList = new ArrayList<>();
m = (InputMethodManager)getSystemService(Context.INPUT_METHOD_SERVICE);
// 獲取屏幕高度
screenHeight = this.getWindowManager().getDefaultDisplay().getHeight();
// 閥值設置爲屏幕高度的1/3
keyHeight = screenHeight / 3;
mXCFlowLayout.setChildView(list, this);
mXCFlowLayout.setAddView(new XCFlowLayout.addViewListener() {
@Override
public void addView() {
lin01.setVisibility(View.VISIBLE);
}
@Override
public void BackTag(ArrayList<String> list) {
BackList.clear();
BackList.addAll(list);
APP.mToast("" + BackList.size());
}
@Override
public void Onremove(String tag) {
APP.mToast(tag);
}
});
}
// 監聽軟鍵盤彈出收起的
@Override
public void onLayoutChange(View v, int left, int top, int right,
int bottom, int oldLeft, int oldTop, int oldRight, int oldBottom) {
// old是改變前的左上右下座標點值,沒有old的是改變後的左上右下座標點值
// 現在認爲只要控件將Activity向上推的高度超過了1/3屏幕高,就認爲軟鍵盤彈起
if (oldBottom != 0 && bottom != 0 && (oldBottom - bottom > keyHeight)) {
lin01.setVisibility(View.VISIBLE);
LogUtils.e("onLayoutChange","軟鍵盤彈起");
// 獲取焦點
edit01.setFocusable(true);
edit01.setFocusableInTouchMode(true);
// 顯示光標、
edit01.requestFocus();// 獲取焦點 光標出現
} else if (oldBottom != 0 && bottom != 0
&& (bottom - oldBottom > keyHeight)) {
lin01.setVisibility(View.GONE);
LogUtils.e("onLayoutChange","軟鍵盤隱藏");
edit01.setFocusable(false);
edit01.setFocusableInTouchMode(false);
edit01.setText("");
// 監聽到軟件盤關閉
}
}
@OnClick(R.id.tv_01)
public void onViewClicked() {
String text = edit01.getText().toString();
if (!TextUtil.isEmpty(text)) {
APP.mToast(text);
mXCFlowLayout.addView(text);
m.toggleSoftInput(0, InputMethodManager.HIDE_NOT_ALWAYS);
}
}
@Override
public void onResume() {
super.onResume();
// 添加layout大小發生改變監聽器
lin01.addOnLayoutChangeListener(this);
}
}
由於今天突發瑣事較多,再加上編輯器卡,瞬間把想好咋寫的就給我整沒了,一股生無可戀的趕腳涌了上來!!!,那就先這些了,另外有個學習討論的羣!大家一起討論哈哈!一起開車,與君共勉!。羣號:188089649!轉載請註明出處!謝謝! 本來按照國際慣例是有個Demo的,但是下班了,電腦編輯器卡了,來不及上,等閒暇時間在補,當然也可以加羣找我要哦《搬磚小能手》
應一個小夥伴的要求寫了個demo,於是順便上傳一下!,讓你們久等了,FlowLayoutDemo
修改了下onMeasure的代碼,修改後的demo(下載了原來demo小夥伴注意一下):FlowLayoutDemo