The problem of Alert Dialog's background changing after Android Activity sets the theme background

Posted by cosminb on Sat, 11 May 2019 12:29:47 +0200

If you look closely at the flash page of App, you will find that every time you click on the icon on the desktop of your mobile phone to start the application, a white background (that is, what we usually call a white screen) will appear first, and then you will jump to the flash page. Like this:

On how to solve the white screen problem at startup, you can refer to this blog:
Causes and Solutions of Black/White Flash on Android App Start Page (Splash) . The solution is simple: set the background to the same picture as the flash page in the SplashActivity theme:

    <style name="SplashTheme" parent="Theme.AppCompat.Light.NoActionBar">
        <item name="android:windowNoTitle">true</item>
        <item name="android:windowFullscreen">true</item>
        <item name="android:background">@drawable/splash_bg</item>
    </style>

Then set the theme of SplashActivity to android:theme="@style/SplashTheme" in the manifest file. The following is the effect of removing the white screen:

In practical projects, applications often detect whether there is a new version at startup, and if so, a prompt dialog box will pop up to ask users if they need to update, or to force users to update directly. Dialog boxes we choose the system's native Alert Dialog (v7 package is the best choice for compatibility with the lower version), but I personally prefer to encapsulate it in Dialog Fragment, the code is as follows:

public class UpdateDialog extends DialogFragment {
    @Override
    public Dialog onCreateDialog(Bundle savedInstanceState) {
        AlertDialog.Builder builder = new AlertDialog.Builder(getActivity());
        builder.setTitle("A new version has been detected!");
        builder.setMessage("1,Optimized UI Details;\n2,Fixed a big wave. bug");
        //Update button immediately
        builder.setPositiveButton("Update immediately", new DialogInterface.OnClickListener() {
            @Override
            public void onClick(DialogInterface dialog, int which) {
                //Update operations are performed here
                Toast.makeText(getActivity(), "Perform update operations", Toast.LENGTH_SHORT).show();
                dialog.dismiss();
            }
        });
        //I'll talk about the button later.
        builder.setNegativeButton("Later on", new DialogInterface.OnClickListener() {
            @Override
            public void onClick(DialogInterface dialog, int which) {
                //Jump to Home Page
                SplashActivity activity = (SplashActivity) getActivity();
                activity.toMainPage();
                dialog.dismiss();
            }
        });
        AlertDialog dialog = builder.create();
        dialog.show();
        //To change the button color, you must call it after the show method
        dialog.getButton(AlertDialog.BUTTON_POSITIVE).setTextColor(Color.BLUE);
        dialog.getButton(DialogInterface.BUTTON_NEGATIVE).setTextColor(Color.RED);
        return dialog;
    }
}

Of course, the logic of version updating can't be so simple. We just show a dialog box first. The display of Dialog Fragment is very simple, and only one code call is needed:

new UpdateDialog().show(getFragmentManager(),"VersionUpdate");

After running, it was found that the Alert Dialog style became very weird:


Without the text in the upper left corner, I could hardly see that it was a dialog box. Clearly we use the native Alert Dialog, why does it look like this?

Do you remember that in order to solve the problem of white screen at startup, we set backgrounds to flash page background images in Activity style? Now the background of the dialog box is also this picture. How can it be so coincident? Remove SplashActivity's Style SplashTheme: <item name="android: background"@drawable/splash_bg</item>, and run again to find that the background of the dialog box turns white, which is exactly the style we want:

Now it seems that changing the background of the theme style in Activity also affects the background of other controls, where the background of the Alert Dialog is forced to become a picture of the flash page. So what can be done to start the white screen and keep Dialog's own dialog box?

After my practice, I found that setting the background of Dialog in the code is ineffective. It must be set in the style. We can set a style for Alert Dialog:

    <style name="UpdateDialogStyle" parent="@android:style/Theme.DeviceDefault.Light.Dialog.NoActionBar.MinWidth">
        <!--This line of code is the settingsAlertDialogBackground-->
        <item name="android:background">@android:color/white</item>
    </style>

Here we will set the background of the dialog box to white separately. It should be noted that we must choose the continuation style, that is @android:style/Theme.DeviceDefault.Light.Dialog.NoActionBar.MinWidth. From its name, we can see that it has the following functions:

  1. Light indicates that it is a light-colored theme, that is, the text color of the Title and Message dialog boxes will be black;
  2. NoAction Bar removes the title bar at the top.
  3. MinWidth ensures that it has the smallest width and does not shrink into a ball.

Back in Update Dialog, just set the Alert Dialog style:

        AlertDialog.Builder builder = new AlertDialog.Builder(getActivity(), R.style.UpdateDialogStyle);

All the code has been reflected in the article, the source code will not be put away. Hope to be helpful to everyone, less trampling on some pits.

Topics: Android Fragment Mobile less