fandro
fandro

Reputation: 4903

How to unselect other AppBarToggleButton UWP

I m doing an UWP project, and I'm using the CommandBar. In my command Bar I have multiple AppBarToggleButton, when I click to one of them I wan't that the other AppBarToggleButton are unselect. Is there an options to do that ?

Here is a symple code :

<CommandBar>
<AppBarToggleButton Icon="Shuffle" Label="Shuffle" Click="AppBarButton_Click" />
<AppBarToggleButton Icon="RepeatAll" Label="Repeat" Click="AppBarButton_Click"/>


<CommandBar.Content>
    <TextBlock Text="Now playing..." Margin="12,14"/>
</CommandBar.Content>

Upvotes: 1

Views: 519

Answers (1)

Justin XL
Justin XL

Reputation: 39006

You just need to x:Name your buttons and manually set IsChecked to False whenever the other one is clicked.

private void AppBarButton1_Click(object sender, RoutedEventArgs e)
{
    AppBarButton2.IsChecked = false;
}

Update

A pure XAML solution would be using bindings. Note you will need an InvertedBooleanConverter here.

IsChecked="{x:Bind Toggle1.IsChecked, Converter={StaticResource InvertedBooleanConverter}, Mode=TwoWay}"

Bonus

I really dislike the binding approach so here's a pure XAML solution built with a behavior. Note you will need to first install the XAML Behaviors from the Nuget Package Manager -

Install-Package Microsoft.Xaml.Behaviors.Uwp.Managed -Version 2.0.0

This AutoDeselectToggleButtonBehavior behavior below basically gets all the AppBarToggleButtons once the CommandBar is loaded, subscribe to all their Click events and in the handlers, simply de-select all the other toggles except the clicked one.

public class AutoDeselectToggleButtonBehavior : Behavior<CommandBar>
{
    private IEnumerable<AppBarToggleButton> _toggleButtons;

    protected override void OnAttached()
    {
        AssociatedObject.Loaded += OnLoaded;

        base.OnAttached();
    }

    protected override void OnDetaching()
    {
        foreach (var toggle in _toggleButtons)
        {
            toggle.Click -= OnToggleClick;
        }

        AssociatedObject.Loaded -= OnLoaded;

        base.OnDetaching();
    }

    private void OnLoaded(object sender, RoutedEventArgs e)
    {
        // Children extension method:
        // https://github.com/JustinXinLiu/Continuity/blob/master/Continuity/Extensions/UtilExtensions.cs#L25
        _toggleButtons = AssociatedObject.Children().OfType<AppBarToggleButton>();

        foreach (var toggle in _toggleButtons)
        {
            toggle.Click += OnToggleClick;
        }
    }

    private void OnToggleClick(object sender, RoutedEventArgs e)
    {
        var clickedToggle = (AppBarToggleButton)sender;

        foreach (var toggle in _toggleButtons)
        {
            if (toggle != clickedToggle)
            {
                toggle.IsChecked = false;
            }
        }
    }
}

Once it's in place, just attach it to your CommandBar like the following -

<CommandBar>
    <Interactivity:Interaction.Behaviors>
        <local:AutoDeselectToggleButtonBehavior />
    </Interactivity:Interaction.Behaviors>

Clean and reusable. :)

Upvotes: 6

Related Questions