androidandroid-layoutprogress-baractivity-lifecyclerecreate

ProgressBar setProgress() not working after Activity recreate()


I have a horizontal ProgressBar which is displaying the remaining life in a game. When the life is 0 (ProgressBar progress is 0) the game ends and there is a button RESTART which calls to activity.recreate();. The progress must be shown full again when recreating but it's being shown empty (progress 0).

All is working fine and being recreated correctly but the ProgressBar. The onCreate() method has this lines:

lifeProgressBar = findViewById(R.id.lifeProgressBar);
lifeProgressBar.setMax(4);
lifeProgressBar.setProgress(4);

When recreating the activity, those lines are being called again. Even putting a breakpoint I can see that the progress is 4, but the ProgressBar is being displayed empty, the same as before recreating the activity.

I tried with invalidate, postinvalidate, etc... not worked.

How to solve this?


Solution

  • From recreate documentation:

    public void recreate ()
    

    Cause this Activity to be recreated with a new instance. This results in essentially the same flow as when the Activity is created due to a configuration change -- the current instance will go through its lifecycle to onDestroy() and a new instance then created after it.

    Here are activity life cycle when activity got recreated:

    onSaveInstanceState() // Save current progress of life progress bar (0 in your case)
    onDestroy()
    onCreate() // You fill full life progress bar
    onRestoreInstanceState() // [IMPORTANT] Activity restores previous state and set progress of life progress bar to 0.

    This is expected behavior of Android, if you need to fill full life progress bar after activity got recreated, then you need to do it in onRestoreInstanceState().

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
    
        lifeProgressBar = findViewById(R.id.lifeProgressBar);
        fillFullLifeProgressBar();
    }
    
    private void fillFullLifeProgressBar() {
        lifeProgressBar.setMax(4);
        lifeProgressBar.setProgress(4);
    }
    
    @Override
    protected void onRestoreInstanceState(Bundle savedInstanceState) {
        super.onRestoreInstanceState(savedInstanceState);
    
        // Fill full life progress bar here.
        fillFullLifeProgressBar();
    }