Android项目实战(七十):自定义组件的常用写法

一种思路,提高效率

1、在res-values-attr.xml文件 设置组件的自定义属性

    <declare-styleable name="CCommonLabelView">
        <attr name="title" format="string"/>
        <attr name="subTitle" format="string"/>
        <attr name="titleColor" format="string"/>
        <attr name="value" format="string"/>
        <attr name="valueColor" format="string"/>
        <attr name="placeholder" format="string"/>
        <attr name="showArr" format="string"/>
        <attr name="showDivider" format="string"/>
        <attr name="showRedIcon" format="string"/>
        <attr name="isEnable" format="string"/>
        <attr name="maxLine" format="string"/>
    </declare-styleable>

2、自定义组件

public class CCommonLabelView extends LinearLayout {

    public Context context;
    public String title = ""; // 左侧标题
    public String subTitle = ""; // 左侧小标题
    public int titleColor = getResources().getColor(R.color.text_title); // 左侧标题颜色
    public String value = ""; // 右侧内容
    public int valueColor = getResources().getColor(R.color.btn_color); // 右侧内容颜色

    public String placeholder = ""; // 右侧没有文本的提示内容

    public boolean showArr = false;  // 是否显示右侧箭头
    public boolean showDivider = true; // 是否显示分割线
    public boolean showRedIcon = false; // 是否显示 必须填写的红色星号
    public boolean isEnable = true; // 是否支持编辑
    private int maxLine = 1; // 最大行数

    View.OnClickListener clickListener; // 点击事件
    View.OnLongClickListener longClickListener; // 长按事件

    public CCommonLabelView(Context context) {
        super(context);
        init();
    }

    public CCommonLabelView(Context context, @Nullable @org.jetbrains.annotations.Nullable AttributeSet attrs) {
        super(context, attrs);
        this.context = context;
        TypedArray typedArray = context.obtainStyledAttributes(attrs, R.styleable.CCommonLabelView);
        title = typedArray.getString(R.styleable.CCommonLabelView_title);
        subTitle = typedArray.getString(R.styleable.CCommonLabelView_subTitle);
        titleColor = typedArray.getColor(R.styleable.CCommonLabelView_titleColor,getResources().getColor(R.color.text_title));
        value = typedArray.getString(R.styleable.CCommonLabelView_value);
        valueColor = typedArray.getColor(R.styleable.CCommonLabelView_valueColor,getResources().getColor(R.color.btn_color));
        placeholder = typedArray.getString(R.styleable.CCommonLabelView_placeholder);
        showArr = typedArray.getBoolean(R.styleable.CCommonLabelView_showArr,false);
        showDivider = typedArray.getBoolean(R.styleable.CCommonLabelView_showDivider,true);
        showRedIcon = typedArray.getBoolean(R.styleable.CCommonLabelView_showRedIcon,false);
        isEnable = typedArray.getBoolean(R.styleable.CCommonLabelView_isEnable,true);
        maxLine = typedArray.getInteger(R.styleable.CCommonLabelView_maxLine,1);
        typedArray.recycle();
        init();
    }
    TextView tvTitle,tvRedIcon,tvSubTitle;
    TextView tvValue;
    ImageView imgArrow;
    View line;

    private void init() {
        LinearLayout rootView = (LinearLayout) LayoutInflater.from(context).inflate(R.layout.custom_view_common_label, null);
        tvTitle = rootView.findViewById(R.id.tvTitle); // 左侧标题
        tvSubTitle = rootView.findViewById(R.id.tvSubTitle); // 左侧小标题
        tvValue = rootView.findViewById(R.id.tvValue); // 右侧内容
        imgArrow = rootView.findViewById(R.id.imgArrow); // 右侧箭头
        line = rootView.findViewById(R.id.line); // 分割线
        tvRedIcon = rootView.findViewById(R.id.tvRedIcon); // 红色星号

        // 左侧标题
        tvTitle.setText(title==null?"":title);
        tvTitle.setTextColor(titleColor);

        // 左侧小标题
        tvSubTitle.setText(subTitle==null?"":subTitle);
        tvSubTitle.setVisibility(subTitle==null?GONE:VISIBLE);
        // 星号
        tvRedIcon.setVisibility(showRedIcon?VISIBLE:GONE);
        // 右侧内容
        tvValue.setText(value ==null?"": value);
        tvValue.setTextColor(valueColor);
        tvValue.setHint(placeholder==null?"":placeholder);

        tvValue.setHintTextColor(context.getResources().getColor(R.color.text_hint));
        // 行数
        tvValue.setMaxLines(maxLine);
        tvValue.setSingleLine(maxLine==1?true:false);
        // 是否可以点击
        tvValue.setEnabled(isEnable);
        tvValue.setAlpha(isEnable?1f:0.5f);
        // 右侧箭头
        imgArrow.setVisibility(showArr?VISIBLE:GONE);
        // 分割线
        line.setVisibility(showDivider?VISIBLE:INVISIBLE);

        // 点击事件
        rootView.setOnClickListener(v -> {
            if (isEnable&&clickListener!=null){
                clickListener.onClick(tvValue);
            }
        });
        rootView.setOnLongClickListener(v -> {
            if (isEnable&&longClickListener!=null){
                longClickListener.onLongClick(tvValue);
            }
            return false;
        });
        // 加入容器
        removeAllViews();
        addView(rootView);
    }

    // **** set
// ****** 标题部分
    // 设置标题
    public CCommonLabelView setTitle(Spanny value) {
        tvTitle.setText(value);
        return this;
    }
    // 设置标题
    public CCommonLabelView setTitle(String value) {
        tvTitle.setText(value);
        return this;
    }
    // 设置子标题
    public CCommonLabelView setSubTitle(String value) {
        this.subTitle = value;
        tvSubTitle.setText(subTitle);
        tvSubTitle.setVisibility(subTitle==null?GONE:VISIBLE);
        return this;
    }
    // 设置标题颜色
    public CCommonLabelView setTitleColor(int color) {
        tvTitle.setTextColor(color);
        return this;
    }
    // 设置标题正常字体
    public CCommonLabelView setTitleStyleNormal() {
        tvTitle.setTypeface(null, Typeface.NORMAL);
        return this;
    }

    // ****** 内容部分
    // 设置内容颜色
    public CCommonLabelView setValueColor(int color) {
        tvValue.setTextColor(color);
        return this;
    }
    // 设置内容对齐方式
    public CCommonLabelView setValueGravity(int gravity){
        tvValue.setGravity(gravity);
        return this;
    }
    // 设置内容
    public CCommonLabelView setValue(Spanny value) {
        tvValue.setText(value);
        return this;
    }
    // 设置内容
    public CCommonLabelView setValue(String value) {
        tvValue.setText(value);
        return this;
    }
    // 是否可以编辑
    public CCommonLabelView setEnable(boolean isEnable) {
        this.isEnable = isEnable;
        tvValue.setAlpha(isEnable?1f:0.5f);
        tvValue.setEnabled(isEnable);
        tvValue.setHint("");
        return this;
    }
    // 设置内容点击事件
    public CCommonLabelView setOnClick(View.OnClickListener listener){
        this.clickListener = listener;
        return this;
    }
    // 设置内容长按事件
    public CCommonLabelView setOnLongClick(View.OnLongClickListener listener){
        this.longClickListener = listener;
        return this;
    }

    // ****** 其他
    // 是否显示分割线
    public CCommonLabelView showDivider(boolean show){
        line.setVisibility(show?VISIBLE:GONE);
        return this;
    }
    // 是否显示右侧箭头
    public CCommonLabelView showArrow(boolean show){
        imgArrow.setVisibility(show?VISIBLE:GONE);
        return this;
    }

    // 设置标题标题view的宽度
    public CCommonLabelView setTitleWidth(int width){
        LinearLayout.LayoutParams params = (LinearLayout.LayoutParams) tvTitle.getLayoutParams(); //取控件textView当前的布局参数
        params.width = width;
        tvTitle.setLayoutParams(params);
        return this;
    }


    // get
    // 获取标题组件
    public TextView getTvTitle() {
        return tvTitle;
    }
}

3、布局

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:orientation="vertical"
    android:background="@color/white"
    android:id="@+id/rootView"
    android:paddingHorizontal="@dimen/dp_16"
    android:layout_width="match_parent"
    android:layout_height="wrap_content">
    <!--标准item 图标标题内容箭头 下划线-->
    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:gravity="center_vertical"
        android:paddingVertical="@dimen/dp_14"
        >
        <ImageView
            android:id="@+id/imgIcon"
            android:layout_width="@dimen/small_icon"
            android:layout_height="@dimen/small_icon"
            android:layout_marginRight="@dimen/dp_10"
            android:visibility="gone"
            />
        <LinearLayout
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:orientation="vertical"
            >
            <LinearLayout
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:orientation="horizontal"
                >
                <TextView
                    android:id="@+id/tvTitle"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:gravity="center|left"
                    android:textColor="@color/text_title"
                    tools:text="标题"
                    android:layout_gravity="left"
                    android:textStyle="bold"
                    ></TextView>
                <TextView
                    android:id="@+id/tvRedIcon"
                    android:layout_width="wrap_content"
                    android:layout_height="wrap_content"
                    android:text="*"
                    android:textColor="@color/text_red"
                    android:visibility="gone"
                    android:layout_marginLeft="@dimen/dp_4"
                    ></TextView>
            </LinearLayout>
            <TextView
                android:id="@+id/tvSubTitle"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:gravity="center|left"
                android:textColor="@color/text_hint"
                tools:text="标题"
                android:layout_gravity="left"
                android:textSize="@dimen/sp_12"
                android:textStyle="bold"
                android:visibility="gone"
                ></TextView>
        </LinearLayout>

        <TextView
            android:id="@+id/tvValue"
            android:layout_width="0dp"
            android:layout_weight="1"
            android:gravity="right"
            android:paddingLeft="@dimen/dp_20"
            android:textColor="@color/btn_color"
            android:textColorHint="@color/text_hint"
            android:layout_height="wrap_content"
            tools:text="内容"
            android:singleLine="true"
            android:ellipsize="end"
            android:layout_toLeftOf="@id/imgArrow"
            android:layout_alignParentRight="true"
            ></TextView>
        <ImageView
            android:id="@+id/imgArrow"
            android:layout_width="@dimen/arrow_width"
            android:layout_height="@dimen/arrow_height"
            android:src="@mipmap/right"
            android:layout_marginLeft="@dimen/dp_10"
            ></ImageView>
    </LinearLayout>
    <View
        android:id="@+id/line"
        android:background="@color/line"
        android:layout_width="match_parent"
        android:layout_height="@dimen/dp_0.5"
        ></View>
</LinearLayout>

 4、用法

<plus.ecloud.retail.mvp.ui.view.custom.common.CCommonInputView
                android:id="@+id/lyName"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                app:title="姓名"
                app:showRedIcon="true"
                app:placeholder="请输入"
                ></plus.ecloud.retail.mvp.ui.view.custom.common.CCommonInputView>

 

效果:

image

 

posted @ 2025-09-01 16:05  听着music睡  阅读(7)  评论(0)    收藏  举报