Android 代码实现shape(GradientDrawable详解)

在项目开发过程中经常会遇到自定义图形,然而在日常很多有重复的工作,如一个图形颜色变了或者线框变宽了等等都需要我们重新新建一个shape文件,这样你就会发现资源文件里面多出了很多shape;这里写了一个我在工作中遇到最多的一种Textview的背景色

首先我们要知道要TextView背景样式的有几种

1.圆角(支持定义圆角半径)

2.按下效果(改变边框或者填充色)

3.按下改变文本颜色

基本上也就这些了,先上一张图



基本上就是把shape问代码实现了一遍


先自定义属性

<?xml version="1.0" encoding="utf-8"?>
<resources>

    <declare-styleable name="CustumBgTextView">
        <!--填充色-->
        <attr name="solidColor" format="color"></attr>
        <!--边框色-->
        <attr name="strokeColor" format="color"></attr>
        <!--按下填充色-->
        <attr name="solidTouchColor" format="color"></attr>
        <!---按下边框色-->
        <attr name="strokeTouchColor" format="color"></attr>
        <!--文字按下颜色 -->
        <attr name="textTouchColor" format="color"></attr>

        <attr name="strokeWith" format="integer"></attr>
        <attr name="radius" format="dimension"></attr>
        <attr name="topLeftRadius" format="dimension"></attr>
        <attr name="topRightRadius" format="dimension"></attr>
        <attr name="bottomLeftRadius" format="dimension"></attr>
        <attr name="bottomRightRadius" format="dimension"></attr>

        <!--虚线的间隙-->
       <attr name="dashGap" format="dimension"></attr>
        <!--虚线的宽度-->
        <attr name="dashWidth" format="dimension"></attr>


        <attr name="shapeTpe" format="enum">
            <enum name="rectangle" value="0"></enum>
            <enum name="oval" value="1"></enum>
            <enum name="line" value="2"></enum>
            <enum name="ring" value="3"></enum>
        </attr>

    </declare-styleable>

</resources>

然后是布局

 <com.shape.tools.CustumShapeBgTextView
        android:layout_width="300dp"
        android:layout_height="50dp"
        android:layout_marginTop="16dp"
        android:text="rectangle"
        apps:radius="7dp"
        apps:strokeWith="1"
        android:gravity="center"
        apps:solidColor="#5555ff"
        apps:strokeColor="#000000"

        />

    <com.shape.tools.CustumShapeBgTextView
        android:layout_width="50dp"
        android:layout_height="50dp"
        android:layout_marginTop="16dp"
        android:text="椭圆Oval"
        apps:radius="7dp"
        apps:strokeWith="1"
        apps:strokeColor="#000000"
        apps:textTouchColor="#ffffff"
        android:gravity="center"
        apps:solidColor="#5555ff"
        apps:shapeTpe="oval"
        />

    <com.shape.tools.CustumShapeBgTextView
        android:layout_width="300dp"
        android:layout_height="50dp"
        android:layout_marginTop="16dp"
        android:text="rectangle"
        android:textColor="#000000"
        apps:bottomLeftRadius="25dp"
        apps:topRightRadius="25dp"
        apps:strokeWith="1"
        android:gravity="center"
        apps:strokeColor="#ff0000"
        apps:solidTouchColor="#ff5555"
        apps:strokeTouchColor="#000000"
        apps:textTouchColor="#ffffff"
        apps:shapeTpe="rectangle"
        apps:dashGap="2dp"
        apps:dashWidth="3dp"
        />
    <com.shape.tools.CustumShapeBgTextView
        android:layout_width="fill_parent"
        android:layout_height="50dp"
        android:layout_marginTop="16dp"
        android:text="line"
        android:textColor="#ff0000"
        apps:bottomLeftRadius="25dp"
        apps:topRightRadius="25dp"
        apps:strokeWith="1"
        android:gravity="center"
        apps:strokeColor="#ff0000"
        apps:solidTouchColor="#ff5555"
        apps:strokeTouchColor="#000000"
        apps:textTouchColor="#000"
        apps:shapeTpe="line"
        android:layerType="software"
        apps:dashGap="2dp"
        apps:dashWidth="3dp"
        />
    <com.shape.tools.CustumShapeBgTextView
        android:layout_width="50dp"
        android:layout_height="50dp"
        android:layout_marginTop="16dp"
        android:text="ring"
        android:textColor="#ff0000"
        apps:bottomLeftRadius="25dp"
        apps:topRightRadius="25dp"
        apps:strokeWith="5"
        android:gravity="center"
        apps:strokeColor="#ff0000"
        apps:solidTouchColor="#ff5555"
        apps:strokeTouchColor="#000000"
        apps:textTouchColor="#000"
        apps:shapeTpe="ring"
        apps:dashGap="2dp"
        apps:dashWidth="3dp"
        />


注意别忘记了在布局头部的命名空间

xmlns:apps="http://schemas.android.com/apk/res-auto"


好了看看正文吧

/**
 * Created by guof on 2016/8/3.
 */
public class CustumShapeBgTextView extends TextView {

    /**
     * 实现自定义圆角背景
     * 支持
     * 1.四边圆角
     * 2.指定边圆角
     * 3.支持填充色以及边框色
     * 4.支持按下效果
     */

    public CustumShapeBgTextView(Context context, AttributeSet attrs) {
        super(context, attrs);
        init(context, attrs);
    }


    private GradientDrawable gd;
    //填充色
    private int solidColor = 0;
    //边框色
    private int strokeColor = 0;
    //按下填充色
    private int solidTouchColor = 0;
    //按下边框色
    private int strokeTouchColor = 0;
    //边框宽度
    private int strokeWith = 0;
    private int shapeTpe = 0;
   //按下字体色
    private int textTouchColor=0;
    //字体色
    private int textColor=0;

    float dashGap=0;
    float dashWidth=0;
    public void init(Context context, AttributeSet attrs) {
        TypedArray ta = context.getTheme().obtainStyledAttributes(attrs, R.styleable.CustumBgTextView, 0, 0);

        solidColor = ta.getInteger(R.styleable.CustumBgTextView_solidColor, 0x00000000);
        strokeColor = ta.getInteger(R.styleable.CustumBgTextView_strokeColor, 0x00000000);

        solidTouchColor = ta.getInteger(R.styleable.CustumBgTextView_solidTouchColor, 0x00000000);
        strokeTouchColor = ta.getInteger(R.styleable.CustumBgTextView_strokeTouchColor, 0x00000000);
        textTouchColor= ta.getInteger(R.styleable.CustumBgTextView_textTouchColor, 0x00000000);
        textColor=getCurrentTextColor();
        strokeWith = ta.getInteger(R.styleable.CustumBgTextView_strokeWith, 0);

        float radius = ta.getDimension(R.styleable.CustumBgTextView_radius, 0);
        float topLeftRadius = ta.getDimension(R.styleable.CustumBgTextView_topLeftRadius, 0);
        float topRightRadius = ta.getDimension(R.styleable.CustumBgTextView_topRightRadius, 0);
        float bottomLeftRadius = ta.getDimension(R.styleable.CustumBgTextView_bottomLeftRadius, 0);
        float bottomRightRadius = ta.getDimension(R.styleable.CustumBgTextView_bottomRightRadius, 0);
          dashGap = ta.getDimension(R.styleable.CustumBgTextView_dashGap, 0);
          dashWidth = ta.getDimension(R.styleable.CustumBgTextView_dashWidth, 0);


        shapeTpe= ta.getInt(R.styleable.CustumBgTextView_shapeTpe, GradientDrawable.RECTANGLE);

        Log.d("sss", "打印shapeTpe" + shapeTpe);

        gd = new GradientDrawable();

        gd.setShape(shapeTpe);
        //矩形
        if (shapeTpe == GradientDrawable.RECTANGLE) {
            gd.setShape(GradientDrawable.RECTANGLE);
            if (radius != 0) {
                gd.setCornerRadius(radius);
            } else {
                //分别表示 左上 右上 右下 左下
                gd.setCornerRadii(new float[]{topLeftRadius, topLeftRadius, topRightRadius, topRightRadius, bottomRightRadius, bottomRightRadius, bottomLeftRadius, bottomLeftRadius});
            }
        } 


        drowBackgroud(false);
        ta.recycle();
    }

    public void setSelection(boolean selection) {
        drowBackgroud(selection);
    }

    /**
     * 设置按下颜色值
     */
    private void drowBackgroud(boolean isTouch) {
        if (isTouch) {
            if (solidTouchColor != 0)
                gd.setColor(solidTouchColor);

            if (strokeWith != 0 && strokeTouchColor != 0) {
                if(dashGap!=0&&dashGap!=0)
                    gd.setStroke(strokeWith, strokeTouchColor,dashGap,dashGap);
                else
                gd.setStroke(strokeWith, strokeTouchColor);
            }
            if(textTouchColor!=0)
                setTextColor(textTouchColor);
        } else {
            if (solidColor != 0)
                gd.setColor(solidColor);
            else
                gd.setColor(Color.TRANSPARENT);

            if (strokeWith != 0 && strokeColor != 0) {

                if(dashGap!=0&&dashGap!=0)
                    gd.setStroke(strokeWith, strokeColor,dashGap,dashGap);
                else
                    gd.setStroke(strokeWith, strokeColor);
            }else
                gd.setStroke(0, Color.TRANSPARENT);


            if(textTouchColor!=0)
                setTextColor(textColor);
        }

        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
            setBackground(gd);
        }
        postInvalidate();
       
    }

    @Override
    public boolean onTouchEvent(MotionEvent event) {
      
        if (event.getAction() == MotionEvent.ACTION_DOWN) {
            drowBackgroud(true);
        } else {
            drowBackgroud(false);
        }

        return true;
    }
}

基本上都能看懂,没啥复杂的地方


备注:

shape写line虚线的时候发现4.0以上机型很多都没办法显示,后来在xml中

  1. android:layerType="software"  

代码中可以添加:

[java] view plaincopy在CODE上查看代码片派生到我的代码片
  1. line.setLayerType(View.LAYER_TYPE_SOFTWARE, null);  





评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值