meq
meq

Reputation: 110

C# UWP binding splitview IsPaneOpen to viewmodel

I was learning on some stuff on universal windows app when i came across this problem: i want to build a splitview menu with a hamburger button without code behind. so i setup a viewmodel with a property and a command for changing the value of that property. to check if the commmand is fired i included a small messagedialog. i bound the splitview IsPaneOpen to my viewmodel but somehow it does not seem to work.

xaml code

<Page.Resources>
    <vm:PaneViewModel x:Key="viewModel"/>
</Page.Resources>
<StackPanel Background="{ThemeResource ApplicationPageBackgroundThemeBrush}" DataContext="{StaticResource viewModel}" >
    <Button Content="Test" Command="{Binding Path=OpenPane, Mode=TwoWay}" ManipulationMode="All"/>
    <SplitView DisplayMode="CompactInline" 
               x:Name="Splitview"
               OpenPaneLength="150" 
               CompactPaneLength="20" 
               IsPaneOpen="{Binding IsPaneOpen, Mode=TwoWay}">
        <SplitView.Pane>
            <StackPanel Height="400">
                <Button Height="40">
                    <TextBlock Text="Testbutton" Width="100"/>
                </Button>
            </StackPanel>
        </SplitView.Pane>
        <SplitView.Content>
            <TextBlock Margin="30" Text="{Binding ShowAnything, Mode=TwoWay}"/>
        </SplitView.Content>
    </SplitView>
</StackPanel>

ViewModel Code

    internal class PaneViewModel
{
    public PaneViewModel()
    {
        OpenPane = new OpenPaneCommand(this);
    }
    private bool isPaneOpen = true;
    public bool IsPaneOpen
    {
        get
        {
            return isPaneOpen;
        }

        set
        {
            isPaneOpen = value;
        }
    }
    public string ShowAnything { get { return isPaneOpen.ToString(); } }
    public OpenPaneCommand OpenPane { get; set; }

    public void OpenPaneMethod()
    {
        if (isPaneOpen == false)
            isPaneOpen = true;
        else
            isPaneOpen = false;
    }
}

and Command Code

    internal class OpenPaneCommand : ICommand
{
    public OpenPaneCommand(PaneViewModel ViewModel)
    {
        this.viewModel = ViewModel;
    }
    private PaneViewModel viewModel;

    public event EventHandler CanExecuteChanged;

    public bool CanExecute(object parameter)
    {
        return true;
    }

    public void Execute(object parameter)
    {
        Blub();
        viewModel.OpenPaneMethod();
    }
    async private void Blub()
    {
        var dialog = new MessageDialog("Testausgabe");
        await dialog.ShowAsync();
    }

like i said - the messagedialog shows up, but neither the textblock in the splitview.content or ispaneopen seems to change. debuging shows me that my method to change the value does indeed change the value. so i was wondering if my binding or datacontext-setting was off.

Maybe you guys got an hint for me where my missunderstanding comes from.

thanks!

meq

Upvotes: 0

Views: 798

Answers (2)

Tom&#225;š Bezouška
Tom&#225;š Bezouška

Reputation: 1499

Your binding isn't working because the View isn't notified of change on your ViewModel. Your VM needs to implement INotifyPropertyChanged interface and raise the PropertyChanged event whenever your property changes.

So typically you would put something like this to your setter:

...
set 
{
   isPaneOpen = value;
   PropertyChanged?.Invoke(this, new PropertyChangedEventArgs("IsPaneOpen");
}
...

Upvotes: 1

MohamedHamza
MohamedHamza

Reputation: 205

I think your view model should inherit the ObservableObject. and further all properties should be update like below:

 public bool IsPaneOpen
        {
            get { return isPaneOpen; }
            set
            {
                this.Set<bool>(ref this._loisPaneOpendedPendingCount, value);
            }
        }

same for ShowAnything property

Upvotes: 0

Related Questions