简体   繁体   中英

OnResume() causing infinite loop in MainActivity

I've recently added the OnResume method to my main activity, however, after doing this, my app is now stuck in an infinite loop because OnResume is being called repeatedly, but I don't know why.

Any ideas what it is about my MainActivity code that's causing the OnResume method to be called repeatedly? Or is there a way in Android Studio I can trace back to see where the call originates from?

For reference, the reason I want to call recreate in the OnResume method is that the user can change the active theme in another activity, so when I come back to MainActivity I want it to pick up the theme change.

public class MainActivity extends AppCompatActivity {

    Toolbar toolbar;
    TabLayout tabLayout;
    static int errorDelay = 2000;
    ViewPager viewPager;
    PageAdapter pageAdapter;
    TabItem tabAveSpeed;
    TabItem tabDistance;
    TabItem tabTime;



    @Override
    public boolean dispatchTouchEvent(MotionEvent event) {
        if (event.getAction() == MotionEvent.ACTION_DOWN) {
            View v = getCurrentFocus();
            if (v instanceof EditText) {
                Rect outRect = new Rect();
                v.getGlobalVisibleRect(outRect);
                if (!outRect.contains((int) event.getRawX(), (int) event.getRawY())) {
                    v.clearFocus();
                    InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
                    imm.hideSoftInputFromWindow(v.getWindowToken(), 0);
                }
            }
        }
        return super.dispatchTouchEvent(event);
    }


    @Override
    protected void onCreate(Bundle savedInstanceState) {

        if (!PrefUtil.getBool(this, "usedBefore")) {
            PrefUtil.saveInt(this, "distanceSpinnerPref", 0);
            PrefUtil.saveBool(this, "usedBefore", true);
            PrefUtil.saveString(this, "activeThemeColour", "Grey");
        }

        String colour = PrefUtil.getString(this, "activeThemeColour");

        switch (colour) {
            case "Green":
                setTheme(R.style.AppTheme_Green);
                break;
            case "Grey":
                setTheme(R.style.AppTheme_Grey);
                break;
            default:
                setTheme(R.style.AppTheme_Grey);
                break;
        }


        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);


        toolbar = findViewById(R.id.toolbar);
        toolbar.setTitle(getResources().getString(R.string.app_name));
        setSupportActionBar(toolbar);

        tabLayout = findViewById(R.id.tabMenu);
        tabAveSpeed = findViewById(R.id.averageSpeedTab);
        tabDistance = findViewById(R.id.distanceTab);
        tabTime = findViewById(R.id.timeTab);
        viewPager = findViewById(R.id.viewPager);

        pageAdapter = new PageAdapter(getSupportFragmentManager(), tabLayout.getTabCount());
        viewPager.setAdapter(pageAdapter);
        viewPager.addOnPageChangeListener(new TabLayout.TabLayoutOnPageChangeListener(tabLayout));



        tabLayout.addOnTabSelectedListener(new TabLayout.OnTabSelectedListener() {
            @Override
            public void onTabSelected(TabLayout.Tab tab) {
                viewPager.setCurrentItem(tab.getPosition());
            }

            @Override
            public void onTabUnselected(TabLayout.Tab tab) {

            }

            @Override
            public void onTabReselected(TabLayout.Tab tab) {

            }
        });
    }

    @Override
    protected void onResume(){
        super.onResume();
        recreate();
    }

    public void updateTabTitle (String newTitle){
        TabLayout tabLayout;
        tabLayout = findViewById(R.id.tabMenu);
        tabLayout.getTabAt(0).setText(newTitle);
    }
}

As others have mentioned, indiscriminately calling recreate() in your onResume() method is going to give you infinite loops.

You can probably do something like write a value to SharedPreferences whenever the user changes the theme, and then check that value in your onResume() and only call recreate() if the theme has changed.

In your other activity, when the user changes the theme, do this:

PreferencesManager.getDefaultSharedPreferences(context)
        .edit()
        .putBoolean("theme_changed", true)
        .apply();

And then in your other activity, inside onResume() , do this:

SharedPreferences prefs = PreferencesManager.getDefaultSharedPreferences(this);

if (prefs.getBoolean("theme_changed", false)) {
    prefs.edit().remove("theme_changed").apply();
    recreate();
}

In this way, you'll only recreate() when there's a reason to do so, and won't loop forever.

Delete recreate(); from this line:

@Override
protected void onResume(){
    super.onResume();
    //recreate();  - delete this line
}

You can read here in docs what recreate() do.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM