美文网首页自定义View
Android自定义必输红点

Android自定义必输红点

作者: 周蛋蛋 | 来源:发表于2019-08-21 21:08 被阅读0次
image.png

首先看UI给的图形,那个红点,最蠢的方法就是我们写一个TextView在设置一个android:drawablePadding="",但是这样写很不友好,要切图,但是*的话我们直接也可以输入法敲出来,所以还是自定义,以后不管这个点在哪里,我们直接可以用了

第一步:设置属性

在values的文件夹下的attrs.xml中设置属性


image.png
    <declare-styleable name="RequiredTextView">
        <attr name="android:text" />
        <attr name="prefix" format="string|reference" />
        <attr name="prefix_color" format="integer|reference" />
    </declare-styleable>

顺便讲一下属性的意义:

  • reference 参考某一资源ID
<declare-styleable name="名称">
  <attr name = "background" format="reference" />
</declare-styleable>

 <ImageView
      android:layout_width = "42dp"
      android:layout_height = "42dp"
      android:background = "@drawable/图片ID" />
  • color:颜色值
<declare-styleable name="名称">
  <attr name = "textColor" format="color" />
</declare-styleable>

<TextView
      android:layout_width = "42dp"
      android:layout_height = "42dp"
      android:textColor = "#ABABAB" />
  • boolean:布尔值
<declare-styleable name="名称">
  <attr name = "focusable" format="boolean" />
</declare-styleable>
<TextView
      android:layout_width = "42dp"
      android:layout_height = "42dp"
      android:focusable = "true" />
  • string:字符串
<declare-styleable name = "MapView">
    <attr name = "apiKey" format = "string" />
</declare-styleable>

<com.google.android.maps.MapView
   android:layout_width = "fill_parent"
   android:layout_height = "fill_parent"
   android:apiKey = "0jOkQ80oD1JL9C6HAja99uGXCRiS2CGjKO_bc_g" />

属性定义时可以指定多种类型值。

<declare-styleable name = "名称">
  <attr name = "background" format = "reference|color" />
</declare-styleable>
<ImageView
  android:layout_width = "42dip"
  android:layout_height = "42dip"
  android:background = "@drawable/图片ID|#00FF00" />

基本上我们就先介绍常用的这几个

第二步:自定义TextView

public class RequiredTextView extends android.support.v7.widget.AppCompatTextView {
    private String prefix = "*";
    private int prefixColor = Color.RED;

    public RequiredTextView(Context context) {
        super(context);
    }

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


    public RequiredTextView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init(context, attrs);
    }

    /**
     * @param context
     * @param attrs   获取属性的集合
     * SPAN_EXCLUSIVE_INCLUSIVE 不包前包后
     */
    private void init(Context context, AttributeSet attrs) {
        TypedArray typedArray = context.obtainStyledAttributes(attrs, R.styleable.RequiredTextView);
        prefixColor = typedArray.getInteger(R.styleable.RequiredTextView_prefix_color, Color.RED);
        String text = typedArray.getString(R.styleable.RequiredTextView_android_text);
        prefix = typedArray.getString(R.styleable.RequiredTextView_prefix);
        if (TextUtils.isEmpty(prefix)) prefix = "*";
        if (TextUtils.isEmpty(text)) text = "";
        typedArray.recycle();
        setText(text+prefix);

    }
    public void setText(String texts) {
        SpannableString spannableString = new SpannableString(texts);
        spannableString.setSpan(new ForegroundColorSpan(prefixColor), texts.length()-1,texts.length(), Spannable.SPAN_EXCLUSIVE_INCLUSIVE);
        setText(spannableString);
    }
}

android开发者网站上有相关的说明文档:
public View (Context context)是在java代码创建视图的时候被调用,如果是从xml填充的视图,就不会调用这个
public View (Context context, AttributeSet attrs)这个是在xml创建但是没有指定style的时候被调用
public View (Context context, AttributeSet attrs, int defStyle)给View提供一个基本的style,如果我们没有对View设置某些属性,就使用这个style中的属性。


image.png
  • set
    set:表示从layout文件中直接为这个View添加的属性的集合,如:android:layout_width="match_parent"。注意,这里面的属性必然是通过xml配置添加的,也就是由LayoutInflater加载进来的布局或者View`才有这个属性集。

现在你知道为啥我们在自己定义View的时候至少要重写(Context context, AttributeSet set)构造器了吧?因为不重写时,我们将无法获取到layout中配置的属性!!当然,也因为这样,LayoutInflater在inflater布局时会通过反射去调用View的(Context context, AttributeSet attrs)构造器。
set 中实际上又有两种数据来源,当然最后都会包含在set中。一种是直接使用android:layout_width="wrap_content"这种直接指定的,还有一种是通过style="@style/somestyle"这样指定的。

  • attrs
    attrs:int[],每个方法中都有的参数,就是告诉系统需要获取那些属性的值。
  • defStyleAttr

也是自定义一个可以在Theme中配置的样式的关键,先看个栗子吧:
如果我想通过在系统主题里面设置一个样式,修改所有textview的样式,你一般会这么做:
<style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar">
    //在主题中设置textview的style
    <item name="android:textViewStyle">@style/textviewstyle</item>
</style>

<style name="textviewstyle" parent="android:style/Widget.TextView">
    <!--指定一些属性-->
</style>

 public TextView(Context context, AttributeSet attrs) {
    //指定属性textViewStyle为defStyleAttr,然后系统会去搜索Theme中你为这个
    //属性配置的style
    this(context, attrs, com.android.internal.R.attr.textViewStyle);
  }

  • TypedArray
    我们看到在获取到属性值之后,都会返回一个TypedArray对象,它又是什么鬼?TypedArray主要有两个作用,第一是内部去转换attrid和属性值数组的关系;第二是提供了一些类型的自动转化,比如我们getString时,如果你是通过@string/hello这种方式设置的,TypedArray会自动去将ResId对应的string从资源文件中读出来。说到底,都是为了方便我们获取属性参数。

相关文章

  • Android自定义必输红点

    首先看UI给的图形,那个红点,最蠢的方法就是我们写一个TextView在设置一个android:drawableP...

  • 练习demo - 收藏集 - 掘金

    自定义未读消息红点提示 - Android - 掘金未读消息提示,可自定义颜色及Padding 效果展示... A...

  • Android自定义小红点BadgeView

    想全局统一个小红点样式,总是改了这个忘了其他的,而且小红点格式各样,总是满足不了自己的需求,所以心血来潮自己自定义...

  • 2019-12-04 iOS tabBar的 tabBarIte

    如图 如图 红点消失 其它场景的使用 以上为系统tabBar的方法,自定义可自己构造小红点。

  • Android自定义View

    Android自定义View 参考:从此再有不愁自定义View——Android自定义view详解android ...

  • 事实证明一切,实力就是硬道理!

    整天玩的人必输,不会资金规划的人必输,不懂得见好就收的人必输。 初玩SSC,因为谨慎,刚开始或多或少都会赢点 后来...

  • 为什么你玩SSC总是在输!

    整天玩的人必输,不会资金规划的人必输,不懂得见好就收的人必输。 初玩SSC,因为谨慎,刚开始或多或少都会赢点 后来...

  • 事实证明一切,实力让你改变!

    整天玩的人必输,不会资金规划的人必输,不懂得见好就收的人必输。 初玩SSC,因为谨慎,刚开始或多或少都会赢点 后来...

  • 事实证明一切,实力让你改变!

    整天玩的人必输,不会资金规划的人必输,不懂得见好就收的人必输。 初玩SSC,因为谨慎,刚开始或多或少都会赢点 后来...

  • 还在输钱的进来看下

    整天玩的人必输,不会资金规划的人必输,不懂得见好就收的人必输。 初玩SSC,因为谨慎,刚开始或多或少都会赢点 后来...

网友评论

    本文标题:Android自定义必输红点

    本文链接:https://www.haomeiwen.com/subject/dooisctx.html