美文网首页android最新知识
在代码中实现android:tint效果

在代码中实现android:tint效果

作者: 苍蝇的梦 | 来源:发表于2016-12-01 17:05 被阅读6575次

    2016-11-30遇到的一点小问题

    Android着色效果tint

    Android有个tint的着色效果,这样有些纯色图片,如果需要显示别的颜色效果,直接加上就行,特别方便。这个网上一搜就有,效果如图:

    android:tint="@color/x"
    我这个原本是个黑色的图标,加上这句,就可以显示各种颜色。
    使用很简单,直接在XML加上android:tint="@color/colorPrimary"就行;如果是背景,加上android:backgroundTint="@color/colorPrimary"就行,比单纯设置方便多了。
    比如Button如果设置android:background="@color/colorPrimary"为纯颜色,那样会没有点击效果,需要点击效果还需要写个selector效果的drawable。如果要在Android5.0之上显示涟漪效果,还需要在drawable-v21中创建一个同名字的ripple效果的drawable
    XML写法简单,在代码中却有点麻烦。
    网上搜索出来的方法有两种:
    第一种不去区分版本,使用V4包的android.support.v4.graphics.drawable.DrawableCompat
    ImageView image = new ImageView(context);
    Drawable up = ContextCompat.getDrawable(context,R.drawable.ic_sort_up);
    Drawable drawableUp= DrawableCompat.wrap(up);
    DrawableCompat.setTint(drawableUp, ContextCompat.getColor(context,R.color.theme));
    image.setImageDrawable(drawableUp);
    

    第二种只能在API21以上使用

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {    
        ImageView image = new ImageView(context);
        image.setImageResource(R.drawable.ic_sort_down);
        image.setImageTintList(ColorStateList.valueOf(ContextCompat.getColor(context,R.color.theme)));
    }
    

    第一种虽然好用,且向下兼容,但有个问题,就是如果我在A界面使用,先打开A界面,再去打开有使用同一个图片的B界面,会发现即使B界面的该ImageView没使用Tint,也会有对应的着色效果。除非先进入的B界面,或者退出应用。

    看有个DrawableCompat.unwrap(...)方法,试了一下,不管用,stackoverflow找到答案
    http://stackoverflow.com/questions/30945490/drawablecompat-unwrap-is-not-working-pre-lollipop
    试了一下,可以了,完整如下:

    ImageView image = new ImageView(context);
    
    Drawable up = ContextCompat.getDrawable(context,R.drawable.ic_sort_up);
    Drawable drawableUp= DrawableCompat.wrap(up);
    DrawableCompat.setTint(drawableUp, ContextCompat.getColor(context,R.color.theme));
    
    image.setImageDrawable(drawableUp);
    
    layoutParams.addRule(RelativeLayout.RIGHT_OF, text.getId());
    addView(image, layoutParams);
    
    Drawable up1 = ContextCompat.getDrawable(context,R.drawable.ic_sort_up);
    Drawable drawableUp1= DrawableCompat.unwrap(up1);
    DrawableCompat.setTintList(drawableUp1, null);
    

    倒数第三行写的那样,需要重新弄个*Drawable 出来,用的同一个会导致之前设置的着色无效;倒数第二行测试使用wrap();也没出问题;最后一行一定用后面的那个Drawable *,用原来那个也会导致之前设置的着色无效。即使他们放在addView()之后。
    当然,最后三行完整放在image.setImageDrawable(drawable);前面也是没有问题的,这边只是为了方便说明。
    这些只是个人随便写的,又刚好有效,写法不一定对。

    点击效果drawable

    普通点击效果 写在drawable文件

    <?xml version="1.0" encoding="utf-8"?>
    <selector xmlns:android="http://schemas.android.com/apk/res/android" >    
          <item android:state_pressed="true">    
                <shape android:shape="rectangle">        
                      <solid android:color="#33000000"/>   
                 </shape>
          </item>
          <item>    
                <shape android:shape="rectangle">        
                      <solid android:color="#FFFFFF"/>    
               </shape>
          </item>
    </selector>
    

    涟漪点击效果 写在drawable-v21文件

    <?xml version="1.0" encoding="utf-8"?>
    <ripple xmlns:android="http://schemas.android.com/apk/res/android"
            android:color="#33FFFFFF">    
        <item>        
            <shape android:shape="rectangle">            
                <solid android:color="#FFFFFF" />       
           </shape>    
        </item>
    </ripple>
    
    RelativeLayout相对位置设置

    在XML中,RelativeLayout相对位置使用android:layout_toRightOf="@+id/view0"来设置;代码中:

    ImageView image = new ImageView(context);
    LayoutParams lp = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
    lp.addRule(RelativeLayout.RIGHT_OF, text.getId());
    rl.addView(image, lp);
    

    需要注意,相对的控件如果是new出来的TextView text = new TextView(context);,需要调用setId()设置ID,text.setId(Integer.MAX_VALUE - 1000);,否则不生效。
    2016-12-02发现了点问题
    之前图片相对在文字右边,高度差不多,没看出问题,今天换了个长图片就发现高度不是居中了。
    调了一下,贴一下正确代码

    <RelativeLayout    
        android:layout_width="match_parent"    
        android:layout_height="90dp">    
        <TextView        
            android:id="@+id/ddd"        
            android:layout_width="wrap_content"        
            android:layout_height="wrap_content"        
            android:layout_centerInParent="true"        
            android:paddingRight="5dp"        
            android:text="测试"/>    
        <TextView        
            android:layout_width="wrap_content"        
            android:layout_height="wrap_content"        
            android:layout_toRightOf="@+id/ddd"        
            android:layout_centerInParent="true"        
            android:text="你\n好\n啊"/>
    </RelativeLayout>
    
    TextView text = new TextView(context);
    text.setId(Integer.MAX_VALUE - 1000);
    text.setTextSize(16);
    text.setText("文字");
    text.setPadding(0,0,3,0);
    text.setTextColor(ContextCompat.getColorStateList(context,R.color.a));
    LayoutParams params = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
    params.addRule(RelativeLayout.CENTER_IN_PARENT);
    addView(text, params);
    
    ImageView imageView = new ImageView(context);
    imageView.setImageDrawable(isUp ? drawableUp :drawableDown);
    LayoutParams lp = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
    lp.addRule(RelativeLayout.CENTER_IN_PARENT);
    lp.addRule(RelativeLayout.RIGHT_OF , text.getId());
    addView(imageView, lp);
    

    因为是居中,所以不管是在XML还是在代码中,第一个控件一定要写android:layout_centerInParent这个属性,第二个可以android:layout_centerVertical="true"android:layout_centerInParent="true",也要写上,否则无效。代码中第二个的addRule()方法,两个记得要分开写,刚开始写一块lp.addRule(RelativeLayout.CENTER_IN_PARENT|RelativeLayout.RIGHT_OF , text.getId());显示出来很奇怪。效果如图:

    RelativeLayout.RIGHT_OF
    简书Markdown文本编辑模式

    之前一直用的51CTO,不过那边用着感觉太重了,看着累,而且搜索不方便,自己记的东西比较难找到。看简书流行就换过来了。简书有两种文本编辑模式 富文本 和 Markdown,刚写简书不太懂,一直弄不成别人那种代码样式。昨天在帮助那边找了找,看到了 http://www.jianshu.com/p/q81RER 赶紧把之前的改一下。不过第一篇用富文本的竟然没法换成Markdown了,心衰,继续丑下去吧。

    相关文章

      网友评论

        本文标题:在代码中实现android:tint效果

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