Search code examples
xamlxamarinxamarin.formsxamarin-binding

AppThemeBinding an ImageButton's Source using Binding is not working


The template is defined as:

<ContentPage.Resources>
    <DataTemplate x:Key="MenuOptionTemplate">
        <controls:MenuButtonControl />
    </DataTemplate>
</ContentPage.Resources>

<ScrollView Orientation="Vertical">
    <FlexLayout
        AlignContent="Start"
        AlignItems="Start"
        BindableLayout.ItemTemplate="{StaticResource MenuOptionTemplate}"
        BindableLayout.ItemsSource="{Binding MenuOptions}"
        JustifyContent="SpaceEvenly"
        VerticalOptions="Start"
        Wrap="Wrap" />
</ScrollView>

The MenuButtonControl is define as:

...
<ImageButton
    Source="{AppThemeBinding Light={Binding LightImageSource},
                             Dark={Binding DarkImageSource}}"/>
...

MenuOptions is is dynamically generated based on the user's role, but basically each menu option is create like so:

new MenuOption {
  Title = "My Title",
  LightImageSource = "sample_light",
  DarkImageSource = "sample_dark"
}

{Binding LightImageSource} does not work.

So what is the correct way to implement this?


Solution

  • Because AppThemeBinding.Light is a markup extension (inherit from IMarkupExtension) property and not a BindableProperty you cannot use DynamicResource or Binding with it.

    Thus you cannot use AppThemeBinding in this case. But you can use bindings (without AppThemeBinding), converters.. (see answers on the linked question), you just need to add the logic to conditionally set the appropriate image source based on the active theme using:

    Application.Current.RequestedTheme;
    

    Binding image source dynamically on xamarin forms

    AppThemeBinding source

    RequestedTheme

    Edit

    To react on theme changes use the event rather than testing the property RequestedThemeChanged:

    How to detect Xamarin Forms System Theme Change