Android.如何让一个按钮保持按下状态,直到该按钮所创建的操作完成?

6

我有三张图片,分别是button_focused, button_pressed, 和 button_normal。当我按下按钮时,会显示button_pressed图片,并执行与按钮按下相关的操作。

当我停止按下按钮时,操作还在继续,但是按钮会显示回button_normal图片。

我该如何设置按钮在整个操作期间一直显示button_pressed图片,然后再重置为button_normal图片?

谢谢您的时间。


1
安卓怎么知道按钮按下的操作呢?你必须自己管理状态。 - Falmarri
我认为他的意思是Falmarri..他已经在问题开头暗示了他有状态。他想知道的是如何将这些状态与操作链接起来。所以假设他有一个按钮A,当按下时会加载一张照片-当他按下按钮A时,它会在按下时显示为活动状态,但当手指松开时,它会恢复到正常状态(他目前设置的方式),但照片仍在加载中,看起来很奇怪。因此,他想知道是否可以将状态与加载操作相关联。注意:如果user527405是女性,请更改上面所有男性术语为女性。 - tm_forthefuture
7个回答

4

I used a function like

void setHighlighted(boolean highlight) {
    button.setBackgroundResource( highlight
                                ? R.drawable.bbg_pressed
                                : R.drawable.button_background);
}

其中button_background是在button_backgroung.xml中定义的选择器:

<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android" >
    <item android:state_pressed="true" android:drawable="@drawable/bbg_pressed"></item>
    <item android:state_focused="true" android:drawable="@drawable/bbg_selected"></item>
    <item android:drawable="@drawable/bbg_normal"></item>
</selector>

也就是说,这段代码不会干扰Android框架所使用的按下状态;相反,它会改变背景,使按钮看起来被按下了。


3

如果您只需要一个两个状态的按钮,以下内容可能会更清晰:

您不需要自己的 button.xml。您可以使用 Android 的普通 Button

button.setPressed(true) 不起作用,因为当您松开按钮时,Android 会将其重置。尝试先设置另一个按钮的 setPressed 状态以查看效果。

这意味着,要在同一个按钮上使用它,必须进行延迟设置。以下是一个可行的示例。当然,通过长 ID(18..)更改背景的方法也有效。

   private final Handler mHandler = new Handler();
   rootView.findViewById(R.id.yourButton).setOnClickListener(new OnClickListener() {
        @Override
        public void onClick(View v) {
            boolean pressed = false;
            if (v.getTag() instanceof Boolean)
                pressed = (boolean) v.getTag();
            final boolean newPressed = !pressed;
            // setTag to store state
            v.setTag(newPressed);
            final View vRun = v;
            Runnable run = new Runnable() {
                @Override
                public void run() {
                    vRun.setPressed(newPressed);
                }
            };
            mHandler.post(run);
            // mHandler.postDelayed(run, 5);
        }
    });

这应该被接受为答案。关键是“要在同一个按钮上使用它,必须设置延迟”。不幸的是,问题变成了,要使用多长时间的延迟?当我点击得很快时,5毫秒并没有起作用。50毫秒效果更好,但有时如果我点击得非常快,它仍然不起作用。所以我选择了100毫秒。然而,这感觉像是一种hack。 - Mark Cramer

1

作为另一种选择,我想提供我的两分意见。不要使用button.setPressed,因为用户松开按钮后会失去选择器的状态,而是可以使用setSelected(true)。只需确保在完成操作后返回setSelected(false)。

        btn.setOnClickListener( view ->  {
        view.setSelected(true);
    });

将可绘制选择器添加为按钮的背景:
<item android:drawable="@drawable/btn_selected" android:state_selected="true"></item>

1

我使用了

NAME_OF_BUTTON.setImageResource(0xvalueofbutton_pressed image listed in R.java);

然后,当操作终止时,我复制了代码并插入了button_normal的整数值。

我以前是用不同的方法做的,现在我找不到我的备份或代码的硬拷贝了。

再次感谢您的回复。


只是一个小提示,让你的生活更轻松。你不应该使用 R.java 中的值,而是直接引用变量。当 ID 重新创建时,这些值可能会发生变化。因此,最好写成:NAME_OF_BUTTON.setImageResource(R.button_pressed); - Juhani

1
如果您在onClick方法中手动更改按钮中的图像,则当操作完成时,它可以将该按钮的普通图像设置回来。如果操作非常快,则更改可能不会正确显示 - 还可能需要延迟代码。

2
我认为这可能是这里最好的答案,但需要一个例子! - tm_forthefuture

1
使用 (buttonName).setPressed(true),并确保您已经保留了适当的 XML 文件来定义用于按下、聚焦等状态的可绘制对象。

1

虽然这是一个老问题,但我认为我的方法比上面所有的方法都更简单。在按钮的onclick事件中:

thisButton
    .getBackground()
    .setColorFilter(getResources().getColor(R.color.colorAccent), PorterDuff.Mode.MULTIPLY);

我的按钮使用可绘制资源(不确定是否重要),当用户点击其中一个时,我设置所需的颜色滤镜,这种颜色与我用于“按下”状态的颜色相同,因此它看起来像是一直被按下。
要清除它,请使用:
thisButton.getBackground().clearColorFilter();

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接