Как исправить getActionBar метод может производить java.ленг.NullPointerException


я использую панель инструментов в качестве панели действий в действии. Я пытаюсь добавить метод getActionBar().setDisplayHomeAsUpEnabled(true); для активности.java-файл для навигации по старым устройствам.

метод выдает следующее сообщение об ошибке в Android Studio:

вызов метода может привести к java.ленг.NullPointerException

навигация вверх на панели инструментов отлично работает на новых устройствах...теперь я пытаюсь выяснить, как убедиться, что это будет работать для старое устройство. Посоветуйте, пожалуйста.

из сборки.Gradle в:

dependencies {
   compile "com.android.support:appcompat-v7:22.1.0"
}

Из AndroidManifest.XML-код:

android:theme="@style/Theme.AppCompat.NoActionBar.FullScreen" 

из стилей.xml

<style name="Theme.AppCompat.NoActionBar.FullScreen" parent="AppTheme">
<item name="android:windowNoTitle">true</item>
<item name="windowActionBar">false</item>
<item name="android:windowFullscreen">true</item>

из активности.java

public class CardViewActivity extends AppCompatActivity {

   @Override
   protected void onCreate(Bundle savedInstanceState) {
       super.onCreate(savedInstanceState);
       setContentView(R.layout.cardviewinput);

    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);

    if (toolbar != null) {
        // Up navigation to the parent activity for 4.0 and earlier
        getActionBar().setDisplayHomeAsUpEnabled(true);
        toolbar.setNavigationIcon(R.drawable.ic_action_previous_item);
        toolbar.setNavigationOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                onBackPressed();
            }
        });
    }

}
10 65

10 ответов:

На самом деле Android Studio не показывает вам "сообщение об ошибке", это просто предупреждение.

некоторые ответы предлагают использовать утверждение, Dalvik runtime имеет утверждение выключен по умолчанию, поэтому вы должны фактически включить его, чтобы он действительно что-то сделал. В этом случае (утверждение отключено), то, что вы по существу делаете, просто обманывает Android Studio, чтобы не показывать вам предупреждение. Кроме того, я предпочитаю не использовать "assert" в производственном коде.

In мое мнение, что вы должны сделать очень просто.

if(getActionBar() != null){
   getActionBar().setDisplayHomeAsUpEnabled(true);
}

обновление: Если вы используете версию библиотеки поддержки панели действий, вы должны заменить getActionBar () на getSupportActionBar ().

if(getSupportActionBar() != null){
    getSupportActionBar().setDisplayHomeAsUpEnabled(true);
}

во-первых, вам нужно установить панель инструментов как поддержка ActionBar. Тогда, если вы уверены, что он будет там все время, просто утверждайте это как != недействительный. Это скажет компилятору, что это не будет null, поэтому проверка null проходит.

@Override
protected void onCreate(Bundle savedInstanceState)
{
   super.onCreate(savedInstanceState);
   setContentView(R.layout.cardviewinput);

   Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
   setSupportActionBar(toolbar);

   assert getSupportActionBar() != null;
   getSupportActionBar().setDisplayHomeAsUpEnabled(true); // it's getSupportActionBar() if you're using AppCompatActivity, not getActionBar()
}

Спасибо Андрей за ваш ответ. Если у вас есть навигационный ящик или что-то еще, что использует getSupportActionBar() вам нужно добавить assert getSupportActionBar() != null;

мира,

пример:

@Override
public void setTitle(CharSequence title) {
    mTitle = title;
    assert getSupportActionBar() != null;
    getSupportActionBar().setTitle(mTitle);
}

попробуйте это :

private ActionBar getActionBar() {
    return ((AppCompatActivity) getActivity()).getSupportActionBar();
}

то, что я сделал, это переопределить getSupportActionBar() метод в моей базовой деятельности и добавить @NonNull Примечание. Таким образом, я получаю только одно предупреждение lint в базовой активности о том, как я использую @NonNull аннотация для чего-то, что имеет @Nullable Примечание.

    @NonNull
    @Override
    public ActionBar getSupportActionBar() {
        // Small hack here so that Lint does not warn me in every single activity about null
        // action bar
        return super.getSupportActionBar();
    }

добавить assert getSupportActionBar() != null; до getSupportActionBar().setDisplayHomeAsUpEnabled(true);

Я создал универсальный класс, таких как:

public final class Cast
{
    private Cast() {}

    /**
     * Helps to eliminate annoying NullPointerException lint warning.
     */
    @android.support.annotation.NonNull
    public static <T> T neverNull(T value)
    {
        return value;
    }
}

тогда я могу использовать его для любого вызова с предупреждением NullPointerException, для которого я уверен, что это никогда не произойдет, например

final ActionBar actionBar = Cast.neverNull(getSupportActionBar());
actionBar.setDisplayHomeAsUpEnabled(true);
actionBar.setHomeButtonEnabled(true);

P. S. Не забудьте добавить "ком.андроид.поддержка: поддержка-аннотации " к вашему файлу gradle.

 if(actionBar != null) {
  actionBar.setHomeButtonEnabled(true);
  actionBar.setBackgroundDrawable(ContextCompat.getDrawable(mContext,
                                  R.drawable.action_bar_gradient));
 }

использовать эту тему: android:theme="@style/Theme.AppCompat.Light.NoActionBar"

Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
toolbar.setTitle("Title");
setSupportActionBar(toolbar);
ActionBar actionBar = getSupportActionBar();
actionBar.setHomeButtonEnabled(true);
actionBar.setHomeAsUpIndicator(R.drawable.ic_action_previous_item);
actionBar.setDisplayHomeAsUpEnabled(true);

в качестве альтернативы вы можете утверждать actionbar не null.Добавьте утверждение перед вызовом панели действий следующим образом

assert getSupportActionBar() != null;

окончательный фрагмент будет выглядеть следующим образом:

    setSupportActionBar((Toolbar) findViewById(R.id.toolbar));
    assert getSupportActionBar() != null;
    getSupportActionBar().setDisplayHomeAsUpEnabled(true);