4
votes

I have an app for Windows Phone 8.1 and a UWP version of it. I'd like to change the background of the apps dynamically when it is changed in Windows.

Use case would be:

  1. Start the app, the background theme is dark.
  2. Press the home button on the phone
  3. Change the background theme to light
  4. Go back to the app (basically switch to it from the background)
  5. The theme of the app would change automatically to the new theme

I'd like it to be done like this, without a restart. I've seen this in other apps, so it has to be possible somehow, but I can't figure out.

If a restart is required, that is fine too as solution B.

Thanks.

3

3 Answers

5
votes

I would suggest to create settings singleton class that will store AppTheme state and implements INotifyPropertyChanged interface

public class Settings : INotifyPropertyChanged
{
    private static volatile Settings instance;
    private static readonly object SyncRoot = new object();
    private ElementTheme appTheme;

    private Settings()
    {
        this.appTheme = ApplicationData.Current.LocalSettings.Values.ContainsKey("AppTheme")
                            ? (ElementTheme)ApplicationData.Current.LocalSettings.Values["AppTheme"]
                            : ElementTheme.Default;
    }

    public static Settings Instance
    {
        get
        {
            if (instance != null)
            {
                return instance;
            }

            lock (SyncRoot)
            {
                if (instance == null)
                {
                    instance = new Settings();
                }
            }

            return instance;
        }
    }

    public ElementTheme AppTheme
    {
        get
        {
            return this.appTheme;
        }

        set
        {
            ApplicationData.Current.LocalSettings.Values["AppTheme"] = (int)value;
            this.OnPropertyChanged();
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;

    protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        this.PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }
}

Than, you can create Property Settings on page, that will return value of singleton and bind RequestedTheme of Page to AppTheme property

<Page
    x:Class="SamplePage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    RequestedTheme="{x:Bind Settings.AppTheme, Mode=OneWay}">
4
votes

Use ThemeResource instead of StaticResource for the colors which might change at runtime:

{ThemeResource ApplicationPageBackgroundThemeBrush}
0
votes

The answer to my question is that I don't need to set the App.RequestedTheme property in the app.xaml file in order to have the theme of the application follow the one of the OS.

I just thought that it needed to be done manually by code.