Android imageview更改色调以模拟按钮单击

Abh*_*hek 38 android android-ui android-imageview

我有一个imageview,我已经设置了一个从网址获取的位图.在imageview上,我设置了一个打开对话框的onClickListener.

当按下imageview时,我想以某种方式改变色调(使其变暗)以提供类似按钮的点击感觉.

你有什么建议?

Ste*_*son 99

happydude的答案是处理这个问题的最优雅的方法,但遗憾的是(正如评论中所指出的)ImageView的源代码只接受整数(纯色).问题18220已经解决了这个问题几年了,我在那里发布了一个解决方法,我将在这里总结:

扩展ImageView并使用基于新状态设置色调的代码包装drawableStateChanged():

TintableImageView.java

package com.example.widgets;

import android.content.Context;
import android.content.res.ColorStateList;
import android.content.res.TypedArray;
import android.util.AttributeSet;
import android.support.v7.widget.AppCompatImageView;

import com.example.R;

public class TintableImageView extends AppCompatImageView {

    private ColorStateList tint;

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

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

    public TintableImageView(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
        init(context, attrs, defStyle);
    }

    private void init(Context context, AttributeSet attrs, int defStyle) {
        TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.TintableImageView, defStyle, 0);
        tint = a.getColorStateList(R.styleable.TintableImageView_tintColorStateList);
        a.recycle();
    }

    @Override
    protected void drawableStateChanged() {
        super.drawableStateChanged();
        if (tint != null && tint.isStateful())
            updateTintColor();
    }    

    private void updateTintColor() {
        int color = tint.getColorForState(getDrawableState(), 0);
        setColorFilter(color);
    }

}
Run Code Online (Sandbox Code Playgroud)

定义自定义属性:

attrs.xml

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

    <declare-styleable name="TintableImageView">
        <attr name="tintColorStateList" format="reference|color" />
    </declare-styleable>

</resources>
Run Code Online (Sandbox Code Playgroud)

将小部件和自定义属性与您的本地命名空间一起使用而不是Android:

example_layout.xml

<?xml version="1.0" encoding="UTF-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="horizontal">

    <com.example.widgets.TintableImageView
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:src="@drawable/example"
        android:clickable="true"
        app:tintColorStateList="@color/color_selector"/>

</LinearLayout>
Run Code Online (Sandbox Code Playgroud)

然后你可以使用像happydude建议的颜色选择器:

color_selector.xml

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
    <item android:state_pressed="true" android:color="@color/pressed_color"/>
    <item android:color="#00000000"/>
</selector>
Run Code Online (Sandbox Code Playgroud)

  • 这就是我的答案在attrs.xml中定义自定义色调属性的原因.你必须在你的布局中使用自定义**app:tint**而不是**android:tint**.实质上,您正在创建一个新属性,该属性包装本机属性并一次为其提供一种颜色. (3认同)
  • 我正在尝试你的解决方案,但仍然得到`java.lang.NumberFormatException:Invalid int:"@ 2130837701"`当`TintableImageView`中的构造函数调用它的超级...我需要传递`new int [] {R. styleable.TintableImageView_tint}`因为`obtainStyledAttributes`要求一个数组,并在colors.xml中声明`<drawable name ="tab_icon_selector"> @ drawable/tab_icon_selector </ drawable>`以便能够从android中引用它:着色 (2认同)

hap*_*ude 7

一种方法是在按下按钮时使用包含色调颜色的a ColorFilter和a 的组合ColorStateList.ColorStateListres/color目录中的xml 如下所示:

button_pressed.xml

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <item android:state_pressed="true" android:color="@color/pressed_color"/>
    <item android:color="#00000000"/>

</selector>
Run Code Online (Sandbox Code Playgroud)

@color/pressed_color您的色调颜色在哪里(应该是部分透明的).然后在您的ImageView子类中,通过覆盖来应用颜色drawableStateChanged().

@Override
protected void drawableStateChanged() {
    super.drawableStateChanged();

    ColorStateList list = getResources().getColorStateList(R.color.button_pressed);
    int color = list.getColorForState(getDrawableState(), Color.TRANSPARENT);
    setColorFilter(color);
    invalidate();
}
Run Code Online (Sandbox Code Playgroud)

只要按钮的状态发生变化,就会调用此代码并自动设置适当的色调.


Cha*_*ake 0

我必须对其进行测试,但是您应该能够将具有该行为的 xml 设置为 ImageView 可绘制对象,然后将位图设置为 ImageView 背景。