WPF 基于组合框选择使用 MVVM 改变窗口布局

Posted

技术标签:

【中文标题】WPF 基于组合框选择使用 MVVM 改变窗口布局【英文标题】:WPF Change Window Layout Based on Combo Box Selection Using MVVM 【发布时间】:2017-06-12 03:51:24 【问题描述】:

我需要根据用户在组合框中选择的内容来更改窗口的布局。我已经尝试过一种方法可能是什么,但感觉它很笨重并且被黑客攻击在一起。我确定他们必须是更清洁的 MVVM 解决方案。

我的想法是在我的 GroupBox 中有多个停靠面板,其可见性设置为折叠。做出选择后,相应的停靠面板将设置为可见。我试图在视图模型中找到一种方法,但没有成功。我也忍不住认为我的尝试违反了 MVVM。

XAML

<GroupBox Header="Options">
    <Grid>
        <DockPanel LastChildFill="False" x:Name="syncWellHeadersDockPanel" Visibility="Collapsed">
            <Button DockPanel.Dock="Right" Content="Test"></Button>
        </DockPanel>
        <DockPanel LastChildFill="False" x:Name="SyncDirectionalSurveyDockPanel" Visibility="Collapsed">
            <Button DockPanel.Dock="Left" Content="Test02"></Button>
        </DockPanel>

    </Grid>
</GroupBox>

ViewModel - 组合框选定项的属性

private StoredActionsModel _selectedStoredAction = DefaultStoredAction.ToList<StoredActionsModel>()[0];
        public StoredActionsModel SelectedStoredAction
        
            get  return _selectedStoredAction; 
            set
            
                if (value != _selectedStoredAction)
                
                    //  Unset Selected on old value, if there was one
                    if (_selectedStoredAction != null)
                    
                        _selectedStoredAction.Selected = false;
                    
                    _selectedStoredAction = value;
                    //  Set Selected on new value, if there is one
                    if (_selectedStoredAction != null)
                    
                        _selectedStoredAction.Selected = true;
                    
                    OnPropertyChanged("SelectedStoredAction");

                    if (_selectedStoredAction.StoredActionID == 4)
                    
                        //X:SyncWellHeaderDockPanel.visibility = true?????
                    
                
            
        

【问题讨论】:

你需要 bool 到可见性的转换器 - msdn.microsoft.com/en-us/library/… ,你也可以找到其他可以将 bool 转换为可见性的 SO 问题。 【参考方案1】:

这是一种纯 XAML 方式,可以完全按照您的要求进行操作。有点啰嗦。

请注意,我们不再在 DockPanels 的属性中设置 Visibility。如果我们仍然这样做,Style 触发器中设置的值将被属性覆盖。这就是依赖属性的工作方式。

<GroupBox Header="Options">
    <Grid>
        <DockPanel LastChildFill="False" x:Name="syncWellHeadersDockPanel" >
            <Button DockPanel.Dock="Right" Content="Test"></Button>
            <DockPanel.Style>
                <Style TargetType="DockPanel" >
                    <Setter Property="Visibility" Value="Collapsed" />
                    <Style.Triggers>
                        <DataTrigger 
                            Binding="Binding SelectedStoredAction.StoredActionID" 
                            Value="1"
                            >
                            <Setter Property="Visibility" Value="Visible" />
                        </DataTrigger>
                    </Style.Triggers>
                </Style>
            </DockPanel.Style>
        </DockPanel>
        <DockPanel LastChildFill="False" x:Name="SyncDirectionalSurveyDockPanel">
            <Button DockPanel.Dock="Left" Content="Test02"></Button>
            <DockPanel.Style>
                <Style TargetType="DockPanel" >
                    <Setter Property="Visibility" Value="Collapsed" />
                    <Style.Triggers>
                        <DataTrigger 
                            Binding="Binding SelectedStoredAction.StoredActionID" 
                            Value="2"
                            >
                            <Setter Property="Visibility" Value="Visible" />
                        </DataTrigger>
                    </Style.Triggers>
                </Style>
            </DockPanel.Style>
        </DockPanel>
    </Grid>
</GroupBox>

另一种方法是将SelectedStoredAction.StoredActionID 传递给DataTemplateSelector,但这涉及编写知道您的XAML 资源键是什么的C# 代码,我不是粉丝。

【讨论】:

总有一天我会遇到一些困难的事情!

以上是关于WPF 基于组合框选择使用 MVVM 改变窗口布局的主要内容,如果未能解决你的问题,请参考以下文章

窗口加载时WPF级联组合框不绑定

WPF中MVVM子窗口修改数据问题

ItemsControl 组合框 selecteditem C# WPF MVVM

WPF,MVVM从字典中填充级联组合框

选择组合框时设置文本框的属性 WPF XAML

在 WPF / C# 中选择绑定项目后维护组合框文本