WPF绑定未更新可见性

本文关键字:可见性 更新 绑定 WPF | 更新日期: 2023-09-27 18:19:55

绑定到网格可见性时遇到问题。我以前有过这样做的项目,并试图复制以前使用的相同编码,我四处搜索,并根据其他一些文章添加了bool-to-visibility转换器,但仍然一无所获。

到目前为止,我在这个项目中所要做的就是为用户提供一组选项。当他们选择一个选项时,它会显示子选项,或者将它们带到适当的区域。我将绑定设置为一个bool对象,有时还会创建一些小消息框和其他消息框,只是为了让我知道程序是否无处不在。一路上我收到了每一个消息框,所以它似乎到达了每一段代码。

有人能阐明我做错了什么吗?或者给我指明正确的方向吗?

Windows.Resources中的转换器(经过编辑以显示Windows.Resourses中的所有代码)

<Window.Resources>
    <Style TargetType="{x:Type Button}">
        <Setter Property="FontSize" Value="15"/>
        <Setter Property="FontWeight" Value="Bold" />
        <Setter Property="Height" Value="50" />
        <Setter Property="Width" Value="100" />
        <Setter Property="Margin" Value="0,0,0,0" />
        <Setter Property="HorizontalAlignment" Value="Center" />
        <Setter Property="VerticalAlignment" Value="Center" />
    </Style>
    <BooleanToVisibilityConverter x:Key="BooleanToVisibilityConverter" />
</Window.Resources>

窗口其余部分的代码

<Grid>
    <Grid x:Name="grid_mainMenu" Visibility="{Binding MainMenuVisibility, Converter={StaticResource BooleanToVisibilityConverter}}" Margin="0,0,0,20">
        <Grid.RowDefinitions>
            <RowDefinition Height="1*"/>
            <RowDefinition Height="1*"/>
        </Grid.RowDefinitions>
        <Button x:Name="button_Items" Content="Items" Grid.Row="0" Click="button_Items_Click"/>
        <Button x:Name="button_Orders" Content="Orders" Grid.Row="1" Click="button_Orders_Click" />
        <TextBox Text="{Binding StatusMessage, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" Margin="0,0,0,0" HorizontalAlignment="Left"  VerticalAlignment="Top" Height="100" Width="100"/>
    </Grid>
    <Grid x:Name="grid_itemMenu" Visibility="{Binding ItemMenuVisibility, Converter={StaticResource BooleanToVisibilityConverter}}" Margin="0,0,0,20">
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="1*"/>
            <RowDefinition Height="1*"/>
        </Grid.RowDefinitions>
        <Label Content="Item Menu" Grid.Row="0" FontSize="20" FontWeight="Bold" Margin="0,0,0,0" HorizontalAlignment="Center" VerticalAlignment="Center"/>
        <Button Grid.Row="1" x:Name="button_itemMaintenance" Content="Maintenance"/>
        <Button Grid.Row="2" x:Name="button_itemCreation" Content="Create"/>
    </Grid>
    <DockPanel Height="25" Margin="0,0,0,0" VerticalAlignment="Bottom">
        <StatusBar DockPanel.Dock="Bottom">
            <StatusBarItem>
                <TextBlock Text="{Binding StatusMessage, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"/>
            </StatusBarItem>
        </StatusBar>
    </DockPanel>
</Grid>

这是类中的代码

    public bool MainMenuVisibility
    {
        get { return _mainMenuVisibility; }
        set { _mainMenuVisibility = value; RaisePropertyChanged(); }
    }
    public bool ItemMenuVisibility
    {
        get { return _itemMenuVisibility; }
        set
        { _itemMenuVisibility = value; RaisePropertyChanged(); }
    }
    public bool OrderMenuVisibility
    {
        get { return _orderMenuVisibility; }
        set { _orderMenuVisibility = value;  RaisePropertyChanged(); }
    }

主要施工单位

public Menu_View()
    {
        ShowMainMenu();
    }

的几个控件

public void ShowMainMenu()
    {
        MainMenuVisibility = true;
        HideItemMenu();
        HideOrderMenu();
        StatusMessage = "Showing main menu";
    }
    public void HideMainMenu()
    {
        MainMenuVisibility = false;
        StatusMessage = "Hid main menu";
    }
    public void ShowItemMenu()
    {
        try
        {
            //Reaches, but never updates
            ItemMenuVisibility = true;
            HideMainMenu();
            HideOrderMenu();
        }
        catch(Exception error)
        {
            //Never shows anything here
            StatusMessage = "Failed to load item menu";
        }
        finally
        {
            //Does not update, but reaches here
            StatusMessage = "Showing item menu";
        }
    }

程序从显示主菜单开始,当用户单击项目按钮时,它应该显示项目菜单。单击按钮会调用ShowItemMenu()。我已经证实了这种情况确实发生了,而且是按正确的顺序调用的。

我已经验证了ShowItemMenu()确实有效,但放入了构造函数而不是ShowMainMenu()。任何一个都可以正常工作,但都不会在初始加载后导致更新,即使在按下按钮后达到更新。

对不起,如果我没有包括我需要的一切。

编辑:

我相信我实际上同时遇到了两个问题。一个是配置不正确的数据转换器。回答并参考以下内容。

以及我的窗口代码中的一个问题:

public MainWindow()
    {
        InitializeComponent();
        menuView = new Menu_View();
        this.DataContext = new Menu_View();
    }
    Menu_View menuView;

我相信这是问题的一部分。我正在创建menuView类型的menuView。在初始化时,我将menuView分配给了一个新的menuView(),然后将DataContext分配给了新的Menu_View()而不是menuView。所有命令都在更新menuView,而我正在更新分配给DataContext的命令。

WPF绑定未更新可见性

将此converter类添加到您的项目中。

 class BooleanToVisibilityConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        if (value is Boolean && (bool)value)
        {
            return Visibility.Visible;
        }
        return Visibility.Collapsed;
    }
    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        if (value is Visibility && (Visibility)value == Visibility.Visible)
        {
            return true;
        }
        return false;
    }
}

参考

如果您选择,您可以不使用布尔转换器。你不必在后面写任何代码。

<Grid>
    <Grid.Style>
        <Style TargetType="{x:Type Grid}">
            <Setter Property="Visibility" Value="Collapsed" />
            <Style.Triggers>
                <DataTrigger Binding="{Binding Path=MyBoolValue}" Value="True">
                    <Setter Property="Visibility" Value="Visible" />
                </DataTrigger>
            </Style.Triggers>
        </Style>
    </Grid.Style>
</Grid>