C# 如何访问WPF用户控件';视图模型中的s元素是选项卡项的内容?
在WPF应用程序中,我有一个由四个文本框组成的用户控件。六个这样的用户控件组成一个数据模板,我使用它在主窗口中填充TabControl的选项卡项。数据模板的内容通过viewmodel绑定到数据层。 我的问题是,我找不到从视图(主窗口)访问每个单独文本框的IsEnabled属性的方法。使用VisualTreeHelper无助于精确定位文本框,因为作为每个选项卡项内容的viewmodel不是可视的。所以我最多只能得到一个TextBox实例的引用,但它可以同时在所有选项卡上工作。 谁能帮我做这个吗 编辑: 下面是简化的代码片段,以便更好地理解我的问题 UserControl XAML:C# 如何访问WPF用户控件';视图模型中的s元素是选项卡项的内容?,c#,wpf,mvvm,C#,Wpf,Mvvm,在WPF应用程序中,我有一个由四个文本框组成的用户控件。六个这样的用户控件组成一个数据模板,我使用它在主窗口中填充TabControl的选项卡项。数据模板的内容通过viewmodel绑定到数据层。 我的问题是,我找不到从视图(主窗口)访问每个单独文本框的IsEnabled属性的方法。使用VisualTreeHelper无助于精确定位文本框,因为作为每个选项卡项内容的viewmodel不是可视的。所以我最多只能得到一个TextBox实例的引用,但它可以同时在所有选项卡上工作。 谁能帮我做这个吗 编
UserControl x:Class="WpfApplication4.MyModuleFrame"
<!-- ... -->
x:Name="mUserControl">
<Grid>
<!-- ... -->
<TextBox Text="{Binding ItemSource.Ch1, ElementName=mUserControl}" Name="txtCh1"/>
<!-- other textboxes -->
</Grid>
</UserControl>
模块C:
namespace WpfApplication4
{
public class Module: INotifyPropertyChanged
{
private double _ch1;
public double Ch1
{
get { return this._ch1; }
set
{
if (_ch1 == value) return;
_ch1 = value;
OnPropertyChanged("Ch1");
}
}
...
...
...
public event PropertyChangedEventHandler PropertyChanged;
private void OnPropertyChanged(string aNameOfProperty)
{
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs(aNameOfProperty));
}
ViewModel.cs:
namespace WpfApplication4
{
public class MainViewModel: INotifyPropertyChanged
{
public Module Module1 { get; set; }
public Module Module2 { get; set; }
public Module Module3 { get; set; }
public Module Module4 { get; set; }
public Module Module5 { get; set; }
public Module Module6 { get; set; }
public MainViewModel()
{
Module1 = new Module() { Number = "1", Ch1 = 123.4, Ch2 = 123.4, Ch3 = 123.4, Ch4 = 123.4 };
Module2 = new Module() { Number = "2", Ch1 = 123.4, Ch2 = 123.4, Ch3 = 123.4, Ch4 = 123.4 };
Module3 = new Module() { Number = "3", Ch1 = 123.4, Ch2 = 123.4, Ch3 = 123.4, Ch4 = 123.4 };
Module4 = new Module() { Number = "4", Ch1 = 123.4, Ch2 = 123.4, Ch3 = 123.4, Ch4 = 123.4 };
Module5 = new Module() { Number = "5", Ch1 = 123.4, Ch2 = 123.4, Ch3 = 123.4, Ch4 = 123.4 };
Module6 = new Module() { Number = "6", Ch1 = 123.4, Ch2 = 123.4, Ch3 = 123.4, Ch4 = 123.4 };
}
...
public event PropertyChangedEventHandler PropertyChanged;
protected virtual void RaisePropertyChanged(string propertyName)
{
this.VerifyPropertyName(propertyName);
PropertyChangedEventHandler handler = this.PropertyChanged;
if (handler != null)
{
var e = new PropertyChangedEventArgs(propertyName);
handler(this, e);
}
}
主窗口XAML:
<Window x:Class="WpfApplication4.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
<!-- ... -->
Title="Window1" Height="800" Width="1000" x:Name="wndMain"
DataContext = "{StaticResource MainViewModel}">
<Window.Resources>
<DataTemplate x:Key="tabTemplate">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="30" />
<RowDefinition Height="210" />
<RowDefinition Height="30" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<loc:MyModuleFrame Name="mmf1" Grid.Row="1" Grid.Column="0" ItemSource="{Binding Module1}"/>
<loc:MyModuleFrame Name="mmf2" Grid.Row="1" Grid.Column="1" ItemSource="{Binding Module2}"/>
<loc:MyModuleFrame Name="mmf3" Grid.Row="1" Grid.Column="2" ItemSource="{Binding Module3}"/>
<loc:MyModuleFrame Name="mmf4" Grid.Row="1" Grid.Column="3" ItemSource="{Binding Module4}"/>
<loc:MyModuleFrame Name="mmf5" Grid.Row="1" Grid.Column="4" ItemSource="{Binding Module5}"/>
<loc:MyModuleFrame Name="mmf6" Grid.Row="1" Grid.Column="5" ItemSource="{Binding Module6}"/>
</Grid>
</DataTemplate>
</Window.Resources>
<Grid>
<TabControl Grid.Row="0" Name="tabHolder" SelectedIndex="{Binding Selected}" HorizontalAlignment="Stretch" Margin="10" VerticalAlignment="Stretch" Height="Auto" Width="Auto"
ContentTemplate="{StaticResource tabTemplate}">
</TabControl>
</Grid>
</Window>
请随时发布一些代码,以获得更好的信息和来自他人的有用帮助
我尽可能地解释,我希望这有助于:
你提到了ViewModel,所以我认为你使用的是MVVM,这是一个很好的方法。在这种方法中,您可以通过绑定访问UI元素,因此需要在每个级别中公开一个dependencProperty
。Hi!感谢您的反馈!我刚刚添加了代码@埃马德
<Window x:Class="WpfApplication4.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
<!-- ... -->
Title="Window1" Height="800" Width="1000" x:Name="wndMain"
DataContext = "{StaticResource MainViewModel}">
<Window.Resources>
<DataTemplate x:Key="tabTemplate">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
<ColumnDefinition Width="1*" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="30" />
<RowDefinition Height="210" />
<RowDefinition Height="30" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<loc:MyModuleFrame Name="mmf1" Grid.Row="1" Grid.Column="0" ItemSource="{Binding Module1}"/>
<loc:MyModuleFrame Name="mmf2" Grid.Row="1" Grid.Column="1" ItemSource="{Binding Module2}"/>
<loc:MyModuleFrame Name="mmf3" Grid.Row="1" Grid.Column="2" ItemSource="{Binding Module3}"/>
<loc:MyModuleFrame Name="mmf4" Grid.Row="1" Grid.Column="3" ItemSource="{Binding Module4}"/>
<loc:MyModuleFrame Name="mmf5" Grid.Row="1" Grid.Column="4" ItemSource="{Binding Module5}"/>
<loc:MyModuleFrame Name="mmf6" Grid.Row="1" Grid.Column="5" ItemSource="{Binding Module6}"/>
</Grid>
</DataTemplate>
</Window.Resources>
<Grid>
<TabControl Grid.Row="0" Name="tabHolder" SelectedIndex="{Binding Selected}" HorizontalAlignment="Stretch" Margin="10" VerticalAlignment="Stretch" Height="Auto" Width="Auto"
ContentTemplate="{StaticResource tabTemplate}">
</TabControl>
</Grid>
</Window>
namespace WpfApplication4
{
public partial class Window1 : Window
{
protected List<MainViewModel> viewmodels;
public Window1()
{
InitializeComponent();
viewmodels = new List<MainViewModel>();
viewmodels.Add(new MainViewModel());
viewmodels.Add(new MainViewModel());
viewmodels.Add(new MainViewModel());
tabHolder.ItemsSource = viewmodels;
}
}
}