【问题标题】:Access Window property from UserControl child从 UserControl 子访问 Window 属性
【发布时间】:2017-03-20 10:16:38
【问题描述】:

我有一个带有 TabControl 的 MainWindow。每个选项卡都是存在于不同文件中的用户控件。

...
<TabControl>
   <TabItem>
      <local:Tab1>
   </TabItem>
...
   <TabItem>
      <local:Tab2>
   </TabItem>
</TabControl>

这些用户控件的行为应根据访问权限而有所不同。访问权限(一个 int)在登录屏幕后通过以下方式传递给主窗口:

MainWindow mainWindow = new MainWindow(accessRights);
mainWindow.show();

现在我拥有 MainWindow.xaml.cs 的访问权限。但是如何在 UserControls 中访问这些访问权限。

【问题讨论】:

  • 如何创建一个带有静态实例的UserManagement 类,然后让您的UserControl 和任何其他控件、类从该实例中获取int

标签: c# wpf xaml user-controls window


【解决方案1】:

您可以为每个 UserControl 类添加一个依赖属性:

public class Tab1 : UserControl
{
    ...

    public Boolean HasAccess
    {
        get { return (Boolean)this.GetValue(HasAccessProperty); }
        set { this.SetValue(HasAccessProperty, value); }
    }
    public static readonly DependencyProperty HasAccessProperty = DependencyProperty.Register(
      "HasAccess", typeof(Boolean), typeof(Tab1), new PropertyMetadata(false));
}

...并将其绑定到 XAML 标记中父窗口的公共属性:

<TabControl>
    <TabItem>
        <local:Tab1 HasAccess="{Binding Path=WindowProperty, RelativeSource={RelativeSource AncestorType=Window}}" />
    </TabItem>
    ...
</TabControl>

如何:实现依赖属性: https://msdn.microsoft.com/en-us/library/ms750428(v=vs.110).aspx

确保窗口类使用 公共属性 公开访问权限,因为您无法绑定到字段。

另一种选择是在加载后使用UserControl 的代码隐藏中的Window.GetWindow 方法获取对父窗口的引用:

public partial class MyUserControl : UserControl
{
    public MyUserControl()
    {
        InitializeComponent();
        Loaded += (s, e) => 
        {
            MainWindow parentWindow = Window.GetWindow(this) as MainWindow;
            if(parentWindow != null)
            {
                //access property of the MainWindow class that exposes the access rights...
            }
        };
    }
}

【讨论】:

    【解决方案2】:

    将此逻辑添加到您的用户控件:

    MainWindow mw = (MainWindow)this.Parent;
    accessRights = mw.accessRights;
    

    这是逻辑,您可能需要更改上面的代码以匹配语法等。

    【讨论】:

    • 当我在 UserControl 构造函数中使用它时,mw 引用始终为空。
    • 子UserControl构造函数被调用,然后是父构造函数,所以将上述逻辑移到UserControls中的非构造方法中。
    【解决方案3】:

    尝试使用 Prism.Core 中的 EventAggregator,基本上你设置 Publish 方法,在其中传递你的 int 并在该用户控件中订阅该事件,事件将在你的情况下加载窗口。

    主窗口视图模型

       public MainWindowViewModel( IEventAggregator eventAggregator)
        {
            eventAggregator.GetEvent<PassingIntToUserControlEvent>().Publish(HereGoesYourInt);
        }
    

    用户控制视图模型

     public UserControlViewModel( IEventAggregator eventAggregator)
        {
            eventAggregator.GetEvent<PassingIntToUserControlEvent>().Subscribe(SomeMethodYouWantWithYourInt);
        }
    

    设置 PassingIntToUserControlEvent 非常简单。

    public class PassingIntToUserControlEvent : PubSubEvent<int>{}
    

    你要开始了。

    此视频对 Prism 及其部分组件进行了基本介绍,其中之一是 EventAggregator。我发现它非常有用。希望能帮助到你。 https://www.youtube.com/watch?v=ZfBy2nfykqY

    【讨论】:

      【解决方案4】:

      在创建时将 MainWindow 实例的引用传递给 UserControl 实例的构造函数。通过这样做,您可以在 UserControls 代码中访问包含主窗体的公共属性。

      【讨论】:

      • 但是我在 xaml 中创建了 UserControl 实例。那我怎样才能通过引用呢?
      • 糟糕,错过了 WPF 部分 ;-) 所以也许你可以在 UserControl 中使用 Window parentWindow = Window.GetWindow(this); 来访问包含的主窗口。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-12-07
      • 1970-01-01
      相关资源
      最近更新 更多