android自定义view基础

该文章笔记代码是从慕课网自定义view课程中学习到的,有兴趣的同学可以学习一下

我们需要实现的自定义view的样式


android自定义view基础_第1张图片
1508123594281.jpg

看似简单其实,两个button,一个textview,但是其实用自定义都是需要我们在class中挨个添加的而且,这个耦合性低,更好当作一个应用的标题工具类进行扩展

第一步

创建一个自定义view的视图,我们需要把命名空间需要自己定义的属性给定义好
android自定义view基础_第2张图片
1508122866605.jpg
  • 在res/values/文件夹下创建attrs.xml文件,用来自定义属性
  • 需要声明 declare-styleable 属性名,这是我们自定义的一些属性名,在这里要注意一下format为属性格式,reference与color一起定义的话可以引用drawable下的图片或者十六进制的颜色格式。


    
        
        
        

        
        
        

        
        
        
    


  • 自定义一个类继承自RelativeLayout,用相对布局进行实现,当然线性布局也可以
package com.yinhao.myui;

import android.content.Context;
import android.content.res.TypedArray;
import android.graphics.drawable.Drawable;
import android.util.AttributeSet;
import android.view.Gravity;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.RelativeLayout;
import android.widget.TextView;

/**
 * Created by yinhao on 2017/10/13.
 */

public class Topbar extends RelativeLayout {

    private Button leftButton, rightButton;
    private TextView tvTitle;

    private int leftTextColor;
    private Drawable leftBackground;
    private String leftText;

    private int rightTextColor;
    private Drawable rightBackground;
    private String rightText;

    private int titleTextColor;
    private float titleTextSize;
    private String title;

    private LayoutParams leftParams, rightParams, titleParams;

    private TopbarClickListener listener;

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

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

    public Topbar(final Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        TypedArray ta = context.obtainStyledAttributes(attrs, R.styleable.Topbar);

        leftTextColor = ta.getColor(R.styleable.Topbar_leftTextColor, 0);
        leftBackground = ta.getDrawable(R.styleable.Topbar_leftBackground);
        leftText = ta.getString(R.styleable.Topbar_leftText);

        rightTextColor = ta.getColor(R.styleable.Topbar_rightTextColor, 0);
        rightBackground = ta.getDrawable(R.styleable.Topbar_rightBackground);
        rightText = ta.getString(R.styleable.Topbar_rightText);

        titleTextSize = ta.getDimension(R.styleable.Topbar_titleTextSize, 0);
        titleTextColor = ta.getColor(R.styleable.Topbar_titleTextColor, 0);
        title = ta.getString(R.styleable.Topbar_title);

        ta.recycle();//回收,避免浪费资源,避免因为缓存引起的一些错误

        leftButton = new Button(context);
        rightButton = new Button(context);
        tvTitle = new TextView(context);

        leftButton.setTextColor(leftTextColor);
        leftButton.setBackground(leftBackground);
        leftButton.setText(leftText);

        rightButton.setTextColor(rightTextColor);
        rightButton.setBackground(rightBackground);
        rightButton.setText(rightText);

        tvTitle.setTextColor(titleTextColor);
        tvTitle.setTextSize(titleTextSize);
        tvTitle.setText(title);
        tvTitle.setGravity(Gravity.CENTER);

        setBackgroundColor(0xfff59563);

        leftParams = new LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        leftParams.addRule(RelativeLayout.ALIGN_PARENT_LEFT, TRUE);
        addView(leftButton, leftParams);

        rightParams = new LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
        rightParams.addRule(RelativeLayout.ALIGN_PARENT_RIGHT, TRUE);
        addView(rightButton, rightParams);

        titleParams = new LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.MATCH_PARENT);
        titleParams.addRule(RelativeLayout.CENTER_IN_PARENT, TRUE);
        addView(tvTitle, titleParams);

        leftButton.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {
                listener.leftClick();
            }
        });

        rightButton.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View v) {
                listener.rightClick();
            }
        });
    }

    public interface TopbarClickListener {
        void leftClick();

        void rightClick();
    }

    public void setOnTopbarClickListener(TopbarClickListener listener) {
        this.listener = listener;
    }
}

  • 我们来分步解释一下代码,在我写的attrs.xml文件中,定义了9个自定义的属性,分别是左边右边按钮的名字,背景和文字颜色。中间是标题名称,文字大小以及颜色。

  • 我们应该如何在类中引用呢?context类中有一个方法obtainStyledAttributes,调用context.obtainStyledAttributes方法返回一个TypedArray类,我们自定义的属性集都在这个类中,参数是我们开始定义的declare-styleable的name值

  • 接着我们就可以调用ta.getXXX的方法把每个单独的自定义属性取出来,这时候的格式是declare-styleable的name值加上每个单独的自定义的值。有些参数为两个参数,第二个为默认值,我们填0即可。

  • 接着我们将自定义的button通过一些我们常用的Button或者TextView的一些方法将从TypedArray中取出来的值进行绑定。

  • 那么现在还差一步,我们只是定义了颜色,可是在哪里声明控件呢?控件的大小怎么办,别急,我们一步步来

  • 控制大小和控件所在的位置,我们需要new一个继承自RelativeLayout的LayoutParams,通过ViewGroup下的LayoutParams设置宽高,接着我们要调用RelativeLayout下特有的方法,通过addRule方法这三个控件相对于布局中的哪个位置,第二个参数为RelativeLayout特有的TRUE值,并非boolean的那种true值。最后通过addView方法将设置好的参数和控件放到咱们的主类里,也就是相对布局里面

  • 如果我们想实现点击方法,我们可以直接写一个setOnClickListener内置的方法去调用,我们也可以一个接口,通过接口,我们降低耦合性,在以后每个不同的activity或者fragment中,自己再进行修改

  • 最后,我们就需要在xml中声明控件了,把Topbar的全类名复制下来,这里要留意下,我们需要自定义一个命名空间,不然会出现找不到属性名的问题。在这里,我定义了一个叫custom的名字。把命名空间最后一个android改成res-auto,如果你用的是eclipse开发项目,可以使用Topbar的全类名。

android自定义view基础_第3张图片
WechatIMG216.jpeg

这样,我们定义的自定义标头就算是完成了。

你可能感兴趣的:(android自定义view基础)