简体   繁体   English

MahApps Metro HamburgerMenu绑定不起作用

[英]MahApps Metro HamburgerMenu Binding Not working

I'm not too sure if this is the best place to ask this but I thought I'd give it a go. 我不太确定这是否是问这个问题的最佳地点,但我想我会尝试一下。

I'm trying to implement a Hamburger Menu into my application using MahApps Metro UI Toolkit which worked great in a test window I made. 我正在尝试使用MahApps Metro UI Toolkit在我的应用程序中实现“汉堡菜单”,该菜单在我创建的测试窗口中效果很好。 So I then started moving to one of my main windows which makes use of a View Model. 因此,我开始移至使用视图模型的主窗口之一。

The problem is, any bindings within the HamburgerMenu do not work at all, but works fine outside of the HamburgerMenu control. 问题是,HamburgerMenu中的所有绑定根本不起作用,但在HamburgerMenu控件外部可以正常工作。

[Example View: [示例视图:

This picture shows the test window mockup I made to show an example. 这张图片显示了我制作的测试窗口模型,以显示一个示例。 The title and both textboxes are all bound to "MyTitle". 标题和两个文本框都绑定到“ MyTitle”。 As you can see, the one within the HamburgerMenu does not work. 如您所见,HamburgerMenu中的那个不起作用。

I have tried binding the ViewModel to the HamburgerMenu control as well which did not work. 我已经尝试将ViewModel绑定到HamburgerMenu控件,这也没有用。 I'd imagine it would have to be bound to "TheContentGrid" or "TheContent" controls within the HamburgerMenu ControlTemplate but those are not accessible from the Code Behind. 我以为它必须绑定到HamburgerMenu ControlTemplate中的“ TheContentGrid”或“ TheContent”控件,但是无法从“隐藏代码”中进行访问。

XAML: XAML:

<Controls:MetroWindow
        ..
        Title="{Binding MyTitle}"
        ..>
    <Grid>
        <Grid.Resources>
            <DataTemplate x:Key="MenuItemTemplate" DataType="{x:Type Controls:HamburgerMenuGlyphItem}">
                <Grid Height="48">
                    <Grid.ColumnDefinitions>
                        <ColumnDefinition Width="48" />
                        <ColumnDefinition />
                    </Grid.ColumnDefinitions>

                    <TextBlock Grid.Column="0" FontSize="16" HorizontalAlignment="Center" VerticalAlignment="Center" FontFamily="Segoe MDL2 Assets" Text="{Binding Glyph}" />
                    <TextBlock Grid.Column="1" VerticalAlignment="Center" FontSize="16" Text="{Binding Label}" />
                </Grid>
            </DataTemplate>
        </Grid.Resources>

        <TextBox Text="{Binding MyTitle}" HorizontalAlignment="Right" />

        <Controls:HamburgerMenu Margin="0 30 0 0"
            SelectedIndex="0"
            x:Name="HamburgerMenuControl"
            ItemTemplate="{StaticResource MenuItemTemplate}"
            OptionsItemTemplate="{StaticResource MenuItemTemplate}"
            ItemClick="HamburgerMenuControl_OnItemClick"
            OptionsItemClick="HamburgerMenuControl_OnItemClick"
            DisplayMode="CompactOverlay">
            <!--  Items  -->
            <Controls:HamburgerMenu.ItemsSource>
                <Controls:HamburgerMenuItemCollection>
                    <Controls:HamburgerMenuGlyphItem Glyph="&#xE80F;" Label="Home">
                        <Controls:HamburgerMenuGlyphItem.Tag>
                            <Grid>
                                <TextBox Text="{Binding MyTitle}" HorizontalAlignment="Center" VerticalAlignment="Top"/>

                                <TextBlock Text="Home View" FontSize="32" HorizontalAlignment="Center" VerticalAlignment="Center" />
                            </Grid>
                        </Controls:HamburgerMenuGlyphItem.Tag>
                    </Controls:HamburgerMenuGlyphItem>
                </Controls:HamburgerMenuItemCollection>
            </Controls:HamburgerMenu.ItemsSource>

            <!--  Content  -->
            <Controls:HamburgerMenu.ContentTemplate>
                <DataTemplate DataType="{x:Type Controls:HamburgerMenuItem}">
                    <Grid x:Name="TheContentGrid">
                        <ContentControl x:Name="TheContent" Content="{Binding Tag}" />
                    </Grid>
                </DataTemplate>
            </Controls:HamburgerMenu.ContentTemplate>
        </Controls:HamburgerMenu>
    </Grid>
</Controls:MetroWindow>

Code Behind & View Model 代码隐藏和视图模型

public partial class WindowTest : MetroWindow
{
    public WindowTest()
    {
        InitializeComponent();

        DataContext = new TestViewModel();
    }

    private void HamburgerMenuControl_OnItemClick(object sender, ItemClickEventArgs e)
    {
        HamburgerMenuControl.Content = e.ClickedItem;
        HamburgerMenuControl.IsPaneOpen = false;
    }
}

public class TestViewModel : BindableBase
{

    private string myTitle;
    public string MyTitle
    {
        get { return myTitle; }
        set { SetProperty(ref myTitle, value); }
    }

    public TestViewModel()
    {
        MyTitle = "Title from VM";
    }
}

Please let me know if more information is required. 如果需要更多信息,请告诉我。

You should solve your problem implementing the INotifyPropertyChanged interface. 您应该解决实现INotifyPropertyChanged接口的问题。

public class TestViewModel : BindableBase, INotifyPropertyChanged
{
    public void SetPropertyChanged(string propertyName)
    {
        PropertyChanged?.Invoke(this, new     PropertyChangedEventArgs(propertyName));
    }
    public event PropertyChangedEventHandler PropertyChanged;
    private string myTitle;
    public string MyTitle
    {
        get { return myTitle; }
        set { 
              SetProperty(ref myTitle, value); 
              SetPropertyChanged("MyTitle");
            }
    }

    public TestViewModel()
    {
        MyTitle = "Title from VM";
    }
}

The problem is that you are not notifying your UI that the Text property of the first textbox is changed. 问题在于您没有通知UI第一个文本框的Text属性已更改。 The UI is initialized before the viewmodel, that's why you see the empty textbox UI在viewmodel之前初始化,这就是为什么您看到空的文本框的原因

Maybe my answer comes a bit late for you but may help others. 也许我的回答对您来说有点晚了,但可能会帮助其他人。 I just stumbled across this issue myself and could resolve it using the solution described in this answer . 我自己偶然发现了这个问题,可以使用此答案中描述的解决方案来解决

Because HamburgerMenuGlyphItem will not be part of the visual or logical tree, there is no binding ancestor for the DataContext . 因为HamburgerMenuGlyphItem不会成为可视树或逻辑树的一部分,所以DataContext没有绑定祖先。 ie your binding has no source to bind to. 即您的绑定没有绑定源。

Create an instance of a helper object in the resources and set the source of the binding explicitly to it using StaticResource : 在资源中创建一个辅助对象的实例,并使用StaticResource显式设置绑定的源:

<Controls:MetroWindow.Resources>
    <local:BindingProxy x:Key="Proxy" Data="{Binding}" />
</Controls:MetroWindow.Resources>
...
    <Controls:HamburgerMenuGlyphItem.Tag>
        <Grid>
            <TextBox Text="{Binding Data.MyTitle, Source={StaticResource Proxy}}" />
        </Grid>
    </Controls:HamburgerMenuGlyphItem.Tag>

Here is the code for the helper object ( source ): 以下是辅助对象( )的代码:

public class BindingProxy : Freezable
{ 
    protected override Freezable CreateInstanceCore()
    {
        return new BindingProxy();
    }

    public object Data
    {
        get { return (object)GetValue(DataProperty); }
        set { SetValue(DataProperty, value); }
    }

    public static readonly DependencyProperty DataProperty =
        DependencyProperty.Register("Data", typeof(object), typeof(BindingProxy), new UIPropertyMetadata(null));
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM