Android 实现计算器布局(自定义View)

上图:

在写计算器布局的时候需要用到这样的页面:

  •      个人觉得最好的实现方式应该是RecycleView

  •       其次可以采用表格布局(这个布局貌似很少使用)

  •       可以用LinearLayout 嵌套 TextView

今天要说的就是LinearLayout 嵌套 TextView

     但是此TextVIew 并非官方,而是我们自定义的View

代码飘一下:


/**
 * 类 名: LineTextView
 * 作 者: yzhg
 * 创 建: 2018/9/20 0020
 * 版 本: 1.0
 * 历 史: (版本) 作者 时间 注释
 * 描 述: 自定义TextView  用于实现计算器页面  绘制四边闲,减少布局
 *
 *    <declare-styleable name="LineTextView">
 *         <attr name="mText" format="string" />
 *         <attr name="mTextColor" format="color" />
 *         <attr name="mTextSize" format="dimension" />
 *         <attr name="mTopLine" format="boolean" />
 *         <attr name="mBottomLine" format="boolean" />
 *         <attr name="mLeftLine" format="boolean" />
 *         <attr name="mRightLine" format="boolean" />
 *         <attr name="mLineWidth" format="dimension" />
 *         <attr name="mLineColor" format="color" />
 *         <attr name="mLineLeftColor" format="color" />
 *         <attr name="mLineRightColor" format="color" />
 *         <attr name="mLineTopColor" format="color" />
 *         <attr name="mLineBottomColor" format="color" />
 *     </declare-styleable>
 */
public class LineTextView extends View {

    /**
     * 需要绘制的文字
     */
    private String mText;
    /**
     * 文本的颜色
     */
    private int mTextColor;
    /**
     * 文本的大小
     */
    private float mTextSize;
    /**
     * 作 者: yzhg
     * 历 史: (版本) 1.0
     * 描 述: 线的宽度
     */
    private float mLineWidth;


    /**
     * 绘制时控制文本绘制的范围
     */
    private Rect mBound;
    private Paint mPaint;

    private Context context;

    private final int DEFAULT_SIZE = 14;

    private float sroke_width = 1;
    private int mLineColor;
    private int mLineTopColor;
    private int mLineBottomColor;
    private int mLineLeftColor;
    private int mLineRightColor;
    private boolean topLine = false;
    private boolean bottomLine = false;
    private boolean leftLine = false;
    private boolean rightLine = false;

    public LineTextView(Context context) {
        this(context, null);
    }

    public LineTextView(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public LineTextView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        this.context = context;
        initAttributes(context, attrs);
        mPaint = new Paint();
        mBound = new Rect();
        mPaint.setTextSize(mTextSize);
        mPaint.setColor(mTextColor);
        mPaint.setStyle(Paint.Style.FILL);
        mPaint.setAntiAlias(true);
        //获取要绘制文字的宽高
        mPaint.getTextBounds(mText, 0, mText.length(), mBound);
    }

    private void initAttributes(Context context, AttributeSet attrs) {
        @SuppressLint({"CustomViewStyleable", "Recycle"})
        TypedArray toolbarArray = context.obtainStyledAttributes(attrs, R.styleable.LineTextView);
        mTextSize = toolbarArray.getDimension(R.styleable.LineTextView_mTextSize, DEFAULT_SIZE);
        mLineWidth = toolbarArray.getDimension(R.styleable.LineTextView_mLineWidth, 0.5f);
        mText = toolbarArray.getString(R.styleable.LineTextView_mText);
        /*
         * 作 者: yzhg
         * 历 史: (版本) 1.0
         * 描 述:  线的方向  top  bottom  left  right all
         */
        topLine = toolbarArray.getBoolean(R.styleable.LineTextView_mTopLine, false);
        bottomLine = toolbarArray.getBoolean(R.styleable.LineTextView_mBottomLine, false);
        leftLine = toolbarArray.getBoolean(R.styleable.LineTextView_mLeftLine, false);
        rightLine = toolbarArray.getBoolean(R.styleable.LineTextView_mRightLine, false);

        /*
         * 作 者: yzhg
         * 历 史: (版本) 1.0
         * 描 述: 设置文字的颜色
         */
        mTextColor = toolbarArray.getColor(R.styleable.LineTextView_mTextColor, context.getResources().getColor(R.color.color_000000));


        /*
         * 作 者: yzhg
         * 历 史: (版本) 1.0
         * 描 述: 设置线的颜色
         */
        mLineColor = toolbarArray.getColor(R.styleable.LineTextView_mLineColor, context.getResources().getColor(R.color.color_CECED2));
        mLineTopColor = toolbarArray.getColor(R.styleable.LineTextView_mLineTopColor, context.getResources().getColor(R.color.color_CECED2));
        mLineBottomColor = toolbarArray.getColor(R.styleable.LineTextView_mLineBottomColor, context.getResources().getColor(R.color.color_CECED2));
        mLineLeftColor = toolbarArray.getColor(R.styleable.LineTextView_mLineLeftColor, context.getResources().getColor(R.color.color_CECED2));
        mLineRightColor = toolbarArray.getColor(R.styleable.LineTextView_mLineRightColor, context.getResources().getColor(R.color.color_CECED2));

        toolbarArray.recycle();
    }


    /*
     * 作 者: yzhg
     * 历 史: (版本) 1.0
     * 描 述: 测量布局
     */
    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        int widthMode = MeasureSpec.getMode(widthMeasureSpec);   //获取宽的模式
        int heightMode = MeasureSpec.getMode(heightMeasureSpec); //获取高的模式
        int widthSize = MeasureSpec.getSize(widthMeasureSpec);   //获取宽的尺寸
        int heightSize = MeasureSpec.getSize(heightMeasureSpec); //获取高的尺寸
        int width;
        int height;
        if (widthMode == MeasureSpec.EXACTLY) {
            //如果match_parent或者具体的值,直接赋值
            width = widthSize;
        } else {
            //如果是wrap_content,我们要得到控件需要多大的尺寸
            float textWidth = mBound.width();   //文本的宽度
            //控件的宽度就是文本的宽度加上两边的内边距。内边距就是padding值,在构造方法执行完就被赋值
            width = (int) (getPaddingLeft() + textWidth + getPaddingRight());
        }
        if (heightMode == MeasureSpec.EXACTLY) {
            height = heightSize;
        } else {
            float textHeight = mBound.height();
            height = (int) (getPaddingTop() + textHeight + getPaddingBottom());
        }
        //保存测量宽度和测量高度
        setMeasuredDimension(width, height);
    }


    @Override
    protected void onDraw(Canvas canvas) {
        /*
         * 作 者: yzhg
         * 历 史: (版本) 1.0
         * 描 述: 控件宽度/2 - 文字宽度/2
         */
        float startX = getWidth() / 2 - mBound.width() / 2;
        /*
         * 作 者: yzhg
         * 历 史: (版本) 1.0
         * 描 述:  控件高度/2 + 文字高度/2,绘制文字从文字左下角开始,因此"+"
         */
        float startY = getHeight() / 2 + mBound.height() / 2;
        /*
         * 作 者: yzhg
         * 历 史: (版本) 1.0
         * 描 述: 绘制文字
         */
        mPaint.setColor(mTextColor);
        canvas.drawText(mText, startX, startY, mPaint);

        /*
         * 作 者: yzhg
         * 历 史: (版本) 1.0
         * 描 述: 绘制边框
         */
        // mPaint.setColor(mLineColor);  //设置边框颜色
        //绘制上方线
        if (topLine) {
            mPaint.setColor(mLineTopColor);
            mPaint.setStrokeWidth(mLineWidth);
            canvas.drawLine(0, 0, this.getWidth() - sroke_width, 0, mPaint);
        }

        //绘制下边框
        if (bottomLine) {
            mPaint.setColor(mLineBottomColor);
            mPaint.setStrokeWidth(mLineWidth);
            canvas.drawLine(0, this.getHeight() - sroke_width, this.getWidth() - sroke_width, this.getHeight() - sroke_width, mPaint);
        }

        //绘制左边框
        if (leftLine) {
            mPaint.setColor(mLineLeftColor);
            mPaint.setStrokeWidth(mLineWidth);
            canvas.drawLine(0, 0, 0, this.getHeight() - sroke_width, mPaint);
        }

        //绘制右边框
        if (rightLine) {
            mPaint.setColor(mLineRightColor);
            mPaint.setStrokeWidth(mLineWidth);
            canvas.drawLine(this.getWidth() - sroke_width, 0, this.getWidth() - sroke_width, this.getHeight() - sroke_width, mPaint);
        }
        super.onDraw(canvas);

    }


    public int dip2px(float dip) {
        //获取屏幕的密度
        float density = context.getResources().getDisplayMetrics().density;
        return (int) (dip * density + 0.5f);
    }

    public float px2dip(float px) {
        float density = context.getResources().getDisplayMetrics().density;
        return px / density;
    }


}

attrs:

   <declare-styleable name="LineTextView">
        <attr name="mText" format="string" />
        <attr name="mTextColor" format="color" />
        <attr name="mTextSize" format="dimension" />
        <attr name="mTopLine" format="boolean" />
        <attr name="mBottomLine" format="boolean" />
        <attr name="mLeftLine" format="boolean" />
        <attr name="mRightLine" format="boolean" />
        <attr name="mLineWidth" format="dimension" />
        <attr name="mLineColor" format="color" />
        <attr name="mLineLeftColor" format="color" />
        <attr name="mLineRightColor" format="color" />
        <attr name="mLineTopColor" format="color" />
        <attr name="mLineBottomColor" format="color" />
    </declare-styleable>

这样就可以减少布局嵌套了

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值