有一種方法可以通過使用DataTriggers來完成您所說的工作。
首先,定義一個Style
,其中包含您要使用的DataTrigger
。例如,這裏需要注意的兩個相同的風格爲ContentControl
,每一個DataTrigger
對執行其它的反面:
<Window.Resources>
<Style TargetType="{x:Type ContentControl}" x:Key="HiddenWhenFalse" >
<Setter Property="Visibility" Value="Collapsed"/>
<Style.Triggers>
<DataTrigger Value="False" Binding="{Binding MyBooleanValue}">
<Setter Property="Visibility" Value="Collapsed" />
</DataTrigger>
<DataTrigger Value="True" Binding="{Binding MyBooleanValue}">
<Setter Property="Visibility" Value="Visible" />
</DataTrigger>
</Style.Triggers>
</Style>
<Style TargetType="{x:Type ContentControl}" x:Key="HiddenWhenTrue" >
<Setter Property="Visibility" Value="Visible"/>
<Style.Triggers>
<DataTrigger Value="True" Binding="{Binding MyBooleanValue}">
<Setter Property="Visibility" Value="Collapsed" />
</DataTrigger>
<DataTrigger Value="False" Binding="{Binding MyBooleanValue}">
<Setter Property="Visibility" Value="Visible" />
</DataTrigger>
</Style.Triggers>
</Style>
</Window.Resources>
然後,在你的主視覺樹中,您將定義ContentControl
S的使用這些Style
S,並將Window
或UserControl
的DataContext
分配給您的ViewModel。事情是這樣的:
<Grid>
<StackPanel >
<Button Content="False" Name="Button2"></Button>
<Button Content="True" Name="Button1"></Button>
<ContentControl Style="{StaticResource HiddenWhenFalse}">
<ContentControl.Content>
<TextBlock Text="ITS ALL TRUE"/>
</ContentControl.Content>
</ContentControl>
<ContentControl Style="{StaticResource HiddenWhenTrue}">
<ContentControl.Content>
<TextBlock Text="ITS ALL FALSE"/>
</ContentControl.Content>
</ContentControl>
</StackPanel>
</Grid>
這裏是我使用,注意INotifyPropertyChanged的實施視圖模型:
Imports System.ComponentModel
Public Class MainWindowViewModel
Implements INotifyPropertyChanged
Private _MyBooleanValue = False
Public Property MyBooleanValue
Get
Return _MyBooleanValue
End Get
Set(ByVal value)
_MyBooleanValue = value
RaiseEvent PropertyChanged(Me, New PropertyChangedEventArgs(Nothing))
End Set
End Property
Public Event PropertyChanged(ByVal sender As Object, ByVal e As System.ComponentModel.PropertyChangedEventArgs) Implements System.ComponentModel.INotifyPropertyChanged.PropertyChanged
End Class
現在,這個樣本的目的,我只是用導線連接了兩個按鈕設置ViewModel值。如果你想使用Commands來連接按鈕,這是一個完全不同的主題。這是值得討論的,但是爲了簡單起見:
Class MainWindow
Private vm As New MainWindowViewModel
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.Windows.RoutedEventArgs) Handles Button1.Click
vm.MyBooleanValue = True
End Sub
Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.Windows.RoutedEventArgs) Handles Button2.Click
vm.MyBooleanValue = False
End Sub
Private Sub MainWindow_Loaded(ByVal sender As Object, ByVal e As System.Windows.RoutedEventArgs) Handles Me.Loaded
Me.DataContext = vm
End Sub
End Class
請記住這個樣本明確風格ContentControl
,那你必須改變你的風格的TargetType的,如果你用工作類型那不是那個階級的後裔。
你爲什麼要這麼做? 簡而言之,「對XAML進行所有更改」的指導原則可能對您沒有意義。我會提供一個代碼示例,但如果它看起來比你完全理解的東西更加複雜或者更難以維護,那麼你會對自己造成傷害。 – 2010-10-05 22:40:57
我對WPF還比較陌生,正在習慣什麼可以被認爲是「最佳實踐」......我看了一個教程,展示了WPF中的MVVM模式,其中出現的部分原因是背後的代碼應該幾乎被剝離...如果你做得對,你的視圖應該幾乎完全是XAML,並且你的ViewModel應該與視圖代碼分離...所以基本上我正在探索不同的方法來組合一個接口可能會根據用戶輸入而改變。 – tbischel 2010-10-05 23:21:37
我知道他們在說什麼。但是,我遇到的每位顧問都將這些事情放入實際實踐中,對這一想法不可知論進行報道。在我看來,它的開發旨在促進將Expression Blend出售給非常大型組織中的混合設計師/開發團隊。 也許這種做法最適合在這些地方以團隊爲基礎的筒倉項目。但對於業務線應用程序,它可能是一個巨大的分心。 但是我會給它這麼多,你會學習複雜的XAML標記。但不要相信,如果它是XAML,那不是代碼。這都是代碼。 – 2010-10-05 23:33:32