Android 自定义的ImageButton状态修改 (Drawable)
2011-02-09 09:27
561 查看
转自:http://blog.sina.com.cn/s/blog_5f8817250100m86s.html
前一段时间,我写一个自定义的ImageButton,其类名MyImageButton。它主要有以下功能:
1,显示文本,手动画上去的,能随意设置文字显示的位置。
2,按下时显示按下的背景图。
3,当disable时,在原来背景图上显示一层半透明。
4,按下去能保持focuse的背景。
5,支持xml属性。
6,能显示overlay图片
7,.......
其实实现这些功能很简单,无非就是画吧,然后就是一堆逻辑处理,按下了没有,是不是应该画focus的背景等等,反正就是画。这些功能由于很简单,并不是我写这篇文章的目的,我主要想说一下如何实现disable的功能。先看看效果图吧。
前两个Button就是自定义的Button,Apply button的状态是enable,cancel
button的状态是disable。这是怎么做的呢?请看下面代码:
Drawable bkDrawable = this.getBackground().mutate();
if (null != bkDrawable)
{
if (enable)
{
bkDrawable.clearColorFilter();
}
else
{
bkDrawable.setColorFilter(m_disableColor,
PorterDuff.Mode.DST_OUT);
}
this.setBackgroundDrawable(bkDrawable);
}
说明一下:
m_disableColor = Color.argb(168, 255, 75,
75);这就是BUTTON不可能时盖在背景上面的颜色。
这几句话的意思就是,如果不可用,enable == false时,就给背景drawable设置color
filter,如果enable == true时,就把color
filter清了,调用clearColorFilter方法。
请注意第一句话中用红色标识出来的方法mutate(),它是干什么的呢?大家可以去查看一个Drawable::muteate方法的说明:
Make this drawable mutable. This operation cannot be reversed. A
mutable drawable is guaranteed to not share its state with any
other drawable. This is especially useful when you need to modify
properties of drawables loaded from resources. By default, all drawables instances loaded
from the same resource share a common state; if you modify the
state of one instance, all the other instances will receive the
same modification.
Calling this method on a mutable Drawable
will have no effect.
翻译过来就是:
使这个drawable变得状态不定。这个操作不能还原(变为不定后就不能变为原来的状态)。一个状态不定的drawable可以保证它不与其他任何一个drawabe共享它的状态。这对于你需要更改从同一资源加载来的drawable的属性时非常有用。默认情况下,所有的从同一资源(R.drawable.XXX)加载来的drawable实例都共享一个共用的状态,如果你更改一个实例的状态,其他所有的实例都会收到相同的通知。
这个方法对于已经是mutable的drawable没有效果。
问题又来了,我这里为什么要用mutate()这个方法呢,不用行吗?答:不用不行,为什么呢?
根据上面的说明,drawable如果是从同一个资源加载来的,这些drawable虽说不是同一实例,但他们共享同一状态,setColorFilter其实就是在改它们的状态,我测试用的例子中的ImageButton,它们的背景资源是同一个,那么这两个ImageButton中的背景drawable就共享同一状态,假如我把Apply设置了disable,那么Cancel中的drawable也成了disable的,所以画出来的就不对了。所以在这里在调用mutate()方法。
下面看看,我不调用mutate()方法的效果,Click me
Button的点击处理是把apply和cancel按钮变为可用或不可用。
this.setContentView(R.layout.atest);
m_apply =
(MyImageButton)this.findViewById(R.id.btnApply1111);
m_cancel =
(MyImageButton)this.findViewById(R.id.btnCancel1111);
m_cancel.setEnabled(false);
Button btn = (Button)this.findViewById(R.id.btnSwitch);
btn.setOnClickListener(new View.OnClickListener()
{
public void onClick(View v)
{
m_apply.setEnabled(!m_apply.isEnabled());
m_cancel.setEnabled(!m_cancel.isEnabled());
}
});
这里我把cancel设置成不可用,按理说应该得到上图那样的效果,看看实际的效果:
不一样了吧,都改了。
所以说,mutate()方法是必须要用的,使每个drawable的状态不相互依赖,相互共享。
前一段时间,我写一个自定义的ImageButton,其类名MyImageButton。它主要有以下功能:
1,显示文本,手动画上去的,能随意设置文字显示的位置。
2,按下时显示按下的背景图。
3,当disable时,在原来背景图上显示一层半透明。
4,按下去能保持focuse的背景。
5,支持xml属性。
6,能显示overlay图片
7,.......
其实实现这些功能很简单,无非就是画吧,然后就是一堆逻辑处理,按下了没有,是不是应该画focus的背景等等,反正就是画。这些功能由于很简单,并不是我写这篇文章的目的,我主要想说一下如何实现disable的功能。先看看效果图吧。
前两个Button就是自定义的Button,Apply button的状态是enable,cancel
button的状态是disable。这是怎么做的呢?请看下面代码:
Drawable bkDrawable = this.getBackground().mutate();
if (null != bkDrawable)
{
if (enable)
{
bkDrawable.clearColorFilter();
}
else
{
bkDrawable.setColorFilter(m_disableColor,
PorterDuff.Mode.DST_OUT);
}
this.setBackgroundDrawable(bkDrawable);
}
说明一下:
m_disableColor = Color.argb(168, 255, 75,
75);这就是BUTTON不可能时盖在背景上面的颜色。
这几句话的意思就是,如果不可用,enable == false时,就给背景drawable设置color
filter,如果enable == true时,就把color
filter清了,调用clearColorFilter方法。
请注意第一句话中用红色标识出来的方法mutate(),它是干什么的呢?大家可以去查看一个Drawable::muteate方法的说明:
Make this drawable mutable. This operation cannot be reversed. A
mutable drawable is guaranteed to not share its state with any
other drawable. This is especially useful when you need to modify
properties of drawables loaded from resources. By default, all drawables instances loaded
from the same resource share a common state; if you modify the
state of one instance, all the other instances will receive the
same modification.
Calling this method on a mutable Drawable
will have no effect.
翻译过来就是:
使这个drawable变得状态不定。这个操作不能还原(变为不定后就不能变为原来的状态)。一个状态不定的drawable可以保证它不与其他任何一个drawabe共享它的状态。这对于你需要更改从同一资源加载来的drawable的属性时非常有用。默认情况下,所有的从同一资源(R.drawable.XXX)加载来的drawable实例都共享一个共用的状态,如果你更改一个实例的状态,其他所有的实例都会收到相同的通知。
这个方法对于已经是mutable的drawable没有效果。
问题又来了,我这里为什么要用mutate()这个方法呢,不用行吗?答:不用不行,为什么呢?
根据上面的说明,drawable如果是从同一个资源加载来的,这些drawable虽说不是同一实例,但他们共享同一状态,setColorFilter其实就是在改它们的状态,我测试用的例子中的ImageButton,它们的背景资源是同一个,那么这两个ImageButton中的背景drawable就共享同一状态,假如我把Apply设置了disable,那么Cancel中的drawable也成了disable的,所以画出来的就不对了。所以在这里在调用mutate()方法。
下面看看,我不调用mutate()方法的效果,Click me
Button的点击处理是把apply和cancel按钮变为可用或不可用。
this.setContentView(R.layout.atest);
m_apply =
(MyImageButton)this.findViewById(R.id.btnApply1111);
m_cancel =
(MyImageButton)this.findViewById(R.id.btnCancel1111);
m_cancel.setEnabled(false);
Button btn = (Button)this.findViewById(R.id.btnSwitch);
btn.setOnClickListener(new View.OnClickListener()
{
public void onClick(View v)
{
m_apply.setEnabled(!m_apply.isEnabled());
m_cancel.setEnabled(!m_cancel.isEnabled());
}
});
这里我把cancel设置成不可用,按理说应该得到上图那样的效果,看看实际的效果:
不一样了吧,都改了。
所以说,mutate()方法是必须要用的,使每个drawable的状态不相互依赖,相互共享。
相关文章推荐
- Android 动态修改自定义drawable圆角,修改边线及填充色
- Android中View(视图)绘制不同状态背景图片原理深入分析以及StateListDrawable使用详解
- android 利用selector设置ImageButton不同状态下的背景图片
- android开发之修改全局自定义字体
- Android 自定义Toast,修改Toast样式和显示时长
- Android中自定义drawable states
- 【android】自定义ProgressDialog实现暂时隐藏进度值并显示等待状态(附源码下载)
- Android 自定义view-如何设置TextView drawableLeft 图片大小?
- Android开发中自定义string、color、style、drawable,title,布局页面(include)的资源使用方法.txt
- Android自定义Drawable
- Android系统默认值的设置与自定义修改
- Android修改状态栏颜色 布局错乱问题解决
- android 怎么判断自定义的控件的显示状态(隐藏、显示)
- Android学习历程22-Android修改状态栏颜色和标题栏颜色一致
- android自定义通知栏,修改通知栏高度 环信
- Android用drawable实现属性按钮3种状态demo
- Android 应用程序窗体显示状态操作(显示隐藏标题栏或自定义窗体大小)
- android 自定义 radiobutton 文字颜色随选中状态而改变
- android 自定义 radiobutton 文字颜色随选中状态而改变
- Android 自定义Drawable