空检查后抛出空错误?

时间:2014-08-27 12:05:26

标签: java android if-statement nullpointerexception

有人可以解释为什么scoreTextSwitcher得到一个空错误,即使我正在检查if语句?只有在启动活动后才会抛出错误 - 更改屏幕方向 - 再次更改屏幕方向 - 然后发生错误...

if(scoreTextSwitcher != null) {
       scoreTextSwitcher.setText(String.valueOf(a));
}

我尝试在下面的链接上寻找答案,但无法弄清楚它与我的代码有什么关系。如果是这样,有人可以澄清一下吗?非常感谢。


这是整个方法(不确定是否在线程中重要)

 private void setScoreTextSwitcher(final int a){
    Thread setScore = new Thread() {
        public void run() {
            if(scoreTextSwitcher == null) {
                scoreTextSwitcher = (TextSwitcher) findViewById(R.id.score_text_switcher);

            }
            GameActivity.this.runOnUiThread(new Runnable() {
                public void run() {
                    if(scoreTextSwitcher != null) {
                        scoreTextSwitcher.setText(String.valueOf(a));
                    }
                }
            });
        }
    };
    setScore.start();
}

以下是错误消息:

08-27 11:02:10.226    2780-2780/com.major.color D/AndroidRuntime﹕ Shutting down VM
08-27 11:02:10.226    2780-2780/com.major.color W/dalvikvm﹕ threadid=1: thread exiting with uncaught exception (group=0x409961f8)
08-27 11:02:10.247    2780-2780/com.major.color E/AndroidRuntime﹕ FATAL EXCEPTION: main
    java.lang.NullPointerException
            at android.widget.TextSwitcher.setText(TextSwitcher.java:78)
            at com.major.color.GameActivity$6$1.run(GameActivity.java:600)
            at android.os.Handler.handleCallback(Handler.java:605)
            at android.os.Handler.dispatchMessage(Handler.java:92)
            at android.os.Looper.loop(Looper.java:137)
            at android.app.ActivityThread.main(ActivityThread.java:4340)
            at java.lang.reflect.Method.invokeNative(Native Method)
            at java.lang.reflect.Method.invoke(Method.java:511)
            at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:784)

这是我的程序的另一部分,也是一个空指针错误。我相信它是同样的问题,因为它只发生在来回启动和改变屏幕方向时。希望这第二个例子可以帮助缩小范围。

 private void startCountDownTimer(){
    isTimerOn = true;
    timerTextSwitcher = (TextSwitcher) findViewById(R.id.timer_text_switcher);
    timer = new CountDownTimer(timerCount, 1000) {
        public void onTick(long millisUntilFinished) {
            isTimerOn = true;
            timerCount = millisUntilFinished;

            if ( millisUntilFinished < 10001) {
                TextView TextSwTextView = (TextView) timerTextSwitcher.getChildAt(0);
                TextSwTextView.setTextColor(Color.RED);
                TextSwTextView.setText(String.valueOf(millisUntilFinished / 1000));
            }else
                if(timerTextSwitcher != null){
                    timerTextSwitcher.setText(String.valueOf(millisUntilFinished / 1000));}else {
                    timerTextSwitcher = (TextSwitcher) findViewById(R.id.timer_text_switcher);
                    timerTextSwitcher.setFactory(new ViewSwitcher.ViewFactory() {

                        public View makeView() {
                            // Create a new TextView and set properties
                            TextView textView = new TextView(getApplicationContext());
                            textView.setLayoutParams(new TextSwitcher.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT));
                            textView.setTextSize(17);
                            textView.setTextColor(Color.BLUE);

                            return textView;
                        }
                    });
                    timerTextSwitcher.setText(String.valueOf(millisUntilFinished / 1000));
                }
        }
   public void onFinish() {
            timerTextSwitcher.post(new Runnable() {
                @Override
                public void run() {
                    createToast("GAME OVER!");
                }
            });
            isTimerOn = false;

            saveScore();
            DialogFragment endDialog = new EndGameFragment();
            Dialog = endDialog;
            endgameVisible = true;
            endDialog.show(getSupportFragmentManager(), "EndGameDialogFragment");
        }
    };
    timer.start();
}

onCreate方法的一部分,显示我如何为得分和活动时间设置TextSwitcher。

 @Override
protected void onCreate(Bundle savedInstanceState) {

    super.onCreate(savedInstanceState);
    getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
            WindowManager.LayoutParams.FLAG_FULLSCREEN);
    setContentView(R.layout.activity_game)
//more code...

 timerTextSwitcher = (TextSwitcher) findViewById(R.id.timer_text_switcher);
    timerTextSwitcher.setFactory(new ViewSwitcher.ViewFactory() {

        public View makeView() {
            // Create a new TextView and set properties
            TextView textView = new TextView(getApplicationContext());
            textView.setLayoutParams(new TextSwitcher.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT));
            textView.setTextSize(17);
            textView.setTextColor(Color.BLUE);

            return textView;
        }
    });
    scoreTextSwitcher = (TextSwitcher) findViewById(R.id.score_text_switcher);
    scoreTextSwitcher.setFactory(new ViewSwitcher.ViewFactory() {

        public View makeView() {
            // Create a new TextView and set properties
            TextView textView = new TextView(getApplicationContext());
            textView.setLayoutParams(new TextSwitcher.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT));
            textView.setTextSize(17);
            textView.setTextColor(Color.BLUE);
            textView.setText("0");
            return textView;
        }
    });

    // Declare the animations and initialize them
    Animation in = AnimationUtils.loadAnimation(this, android.R.anim.slide_in_left);
    Animation out = AnimationUtils.loadAnimation(this, android.R.anim.slide_out_right);

    // set the animation type to textSwitcher
    timerTextSwitcher.setInAnimation(in);
    timerTextSwitcher.setInAnimation(out);
    scoreTextSwitcher.setInAnimation(in);
    scoreTextSwitcher.setInAnimation(out);
}

2 个答案:

答案 0 :(得分:1)

试试这个

private void setScoreTextSwitcher(final int a){
scoreTextSwitcher = (TextSwitcher) findViewById(R.id.score_text_switcher);
Thread setScore = new Thread() {
    public void run() {
        if(scoreTextSwitcher.isEmpty()) {
            Log.e("","Empty");

        }
        GameActivity.this.runOnUiThread(new Runnable() {
            public void run() {
                if(scoreTextSwitcher != null) {
                    scoreTextSwitcher.setText(String.valueOf(a));
                }
            }
        });
    }
};
setScore.start();

}

答案 1 :(得分:1)

以下行导致了不良行为:

private void startCountDownTimer(){
    ...
    timerTextSwitcher = (TextSwitcher) findViewById(R.id.timer_text_switcher);

private void setScoreTextSwitcher(final int a){
    ...
    scoreTextSwitcher = (TextSwitcher) findViewById(R.id.score_text_switcher);

findViewById()的这些调用正在重新初始化切换器,导致他们丢失onCreate()中的工厂和动画设置,并导致NullPointerException中的内部setText() {1}}方法。因为看起来,Switchers在Activity的范围内被声明,你只需要删除那些行。