AppCompat在操作栏中显示进度条导致NPE异常。

12

更新了SDK以获取所有最新的Android 5.0好处后,我不能使用appcompat中内置的ActionBar进度条。我已经尝试了所有通常的修复方法(将supportRequestWindowFeature()调用移至setContent()之前和oncreate中super调用之前),但都无效。这是我的做法:

public class LoginActivity extends ActionBarActivity {
protected void onCreate(Bundle savedInstanceState) {
    supportRequestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
    super.onCreate(savedInstanceState);

    setContentView(R.layout.login);
    ...
    loginButton.setOnClickListener(new View.OnClickListener() {

        @Override
        public void onClick(View v) {
                ...
                setSupportProgressBarIndeterminateVisibility(true);
        }
    });

和调用栈信息:

10-18 19:38:21.053: E/AndroidRuntime(11206): java.lang.NullPointerException: Attempt to invoke     virtual method 'void android.support.v7.internal.widget.ProgressBarCompat.setVisibility(int)' on a null object reference
10-18 19:38:21.053: E/AndroidRuntime(11206):    at android.support.v7.app.ActionBarActivityDelegateBase.updateProgressBars(ActionBarActivityDelegateBase.java:786)
10-18 19:38:21.053: E/AndroidRuntime(11206):    at android.support.v7.app.ActionBarActivityDelegateBase.setSupportProgressBarIndeterminateVisibility(ActionBarActivityDelegateBase.java:692)
10-18 19:38:21.053: E/AndroidRuntime(11206):    at android.support.v7.app.ActionBarActivity.setSupportProgressBarIndeterminateVisibility(ActionBarActivity.java:327)
10-18 19:38:21.053: E/AndroidRuntime(11206):    at com.myapppackage.LoginActivity$2.onClick(LoginActivity.java:82)

这是在运行Android 4.4.4的Nexus 5上。应用程序主题继承自Theme.AppCompat。该应用程序使用Android 5.0构建,目标SDK为21。当我对普通水平进度条使用setSupportProgress时,同样的问题会发生。非常感谢任何帮助。

编辑: 找到了问题。在android.support.v7.internal.widget.ToolbarWidgetWrapper中:

@Override
public void initIndeterminateProgress() {
    Log.i(TAG, "Progress display unsupported");
}

也许不是bug而是特性?工具栏似乎成为了新的操作栏。

我在另一台电脑上有V20 appcompat的副本,所以我会回到那个版本。


2
Chris Banes的确认信息 https://chris.banes.me/2014/10/17/appcompat-v21/#comment-1642002459 - Mark
嘿,马克,我也遇到了同样的问题。我认为现在的重点是你必须在工具栏内制作自己的进度条。基本上就像Chris Banes所说的那样。我正在寻找其他人已经完成的解决方案,这样我就不用自己去尝试了。 - lazypig
4个回答

12

一个可能的解决方法是手动添加一个ProgressBar作为自定义视图,并覆盖setSupportProgressBarIndeterminateVisibility方法。

在onCreate方法中:

ProgressBar progressBar = new ProgressBar(this);
progressBar.setVisibility(View.GONE);
progressBar.setIndeterminate(true);
getSupportActionBar().setDisplayShowCustomEnabled(true);
getSupportActionBar().setCustomView(progressBar);

在您的活动中:

@Override
public void setSupportProgressBarIndeterminateVisibility(boolean visible) {
    getSupportActionBar().getCustomView().setVisibility(visible ? View.VISIBLE : View.GONE);
}

当然,切换到工具栏并在其中添加进度条应该更具未来性。


如果您使用setCustomView并将布局参数设置为gravity top和width match parent,则此方法有效。不幸的是,如果存在标题和3点菜单,则它无法覆盖操作栏的100%宽度。我希望在操作栏右上角有一个圆形样式,但这可能是更时尚的外观。 - Mark
两个进度条出现了,不知道为什么? - user2273146

4

看起来在支持库V21中不支持不确定进度和水平进度条。来自android.support.v7.internal.widget.ToolbarWidgetWrapper:

@Override
public void initIndeterminateProgress() {
    Log.i(TAG, "Progress display unsupported");
}

Chris Banes已经证实了这一点:http://chris.banes.me/2014/10/17/appcompat-v21/#comment-1642002459。我正在使用旧版本的appcompat v20。这里有一个zip文件,供需要的人使用:https://drive.google.com/file/d/0B2dSjU9N8KdZUEFuMkhLZzJZOFU/view?usp=sharing

2

编辑:下面的方法不起作用,因为ProgressBarCompat是一个隐藏的类,不能添加到您的XML布局中。这感觉像是appcompat库中的一个错误。


它在ActionBarActivityDelegateBase.java中寻找进度条:

private ProgressBarCompat getCircularProgressBar() {
    ProgressBarCompat pb = (ProgressBarCompat) mActivity.findViewById(R.id.progress_circular);
    if (pb != null) {
        pb.setVisibility(View.INVISIBLE);
    }
    return pb;
}

在同一个类中的updateProgressBars()方法中使用它。看起来开发人员需要向您的活动添加一个ProgressBarCompat


1
我在我的答案中链接了它,但 Google 正在从 appcompat 库中删除此功能。https://code.google.com/p/android/issues/detail?id=78310 - SWoo

2

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