演练:在 WPF 应用程序中承载第三方 Windows 窗体控件

[本文档仅供预览,在以后的发行版中可能会发生更改。包含的空白主题用作占位符。]

本演练演示如何使用 适用于 Visual Studio 的 WPF 设计器 在 WPF 应用程序中承载一个 windows 窗体第三方供应商控件。 有关 windows 窗体和 WPF 互操作性的更多信息,请 迁移和互操作性参见。

在本演练中,您将使用一个 MonthCalendar 控件来表示第三方供应商控件。 您可以创建一个具有 MonthCalendar 控件实例在其 Controls 集合中的 UserControl 类型。 UserControl 类型显示 Date 属性和实现自定义逻辑定义 MonthCalendar 控件行为。 在 WPF 应用程序中, TextBlock 元素绑定到 Date 属性。

在本演练中,您将执行下列任务:

  • 创建 WPF 项目。

  • 创建一个 windows 窗体用户控件封装供应商控件。

  • 在 WPF 应用程序中承载 windows 窗体用户控件。

下图显示应用程序将如何显示。

寄宿的 Windows 窗体控件

备注

您看到的对话框和菜单命令可能会与 " 帮助 " 中的描述不同具体取决于您现用的设置或版本。若要更改设置,请选择在 工具 菜单的 导入和导出设置 。有关更多信息,请参见 Visual Studio 设置

系统必备

您需要以下组件来完成本演练:

  • Visual Studio 2012 RC.

创建 WPF 项目

第一步是为宿主应用程序创建 WPF 项目。

创建项目

  1. 创建新的 WPF 名为 HostingMonthCalendar的应用程序项目在 Visual Basic 或 Visual C#。 有关更多信息,请参见 如何:创建新的 WPF 应用程序项目

    在 MainWindow.xaml WPF Designer打开。

  2. 解决方案资源管理器,添加一个对名为 WindowsFormsIntegration.dll 的 WindowsFormsIntegration 程序集,。

创建 windows 窗体组合控件

本过程演示如何通过派生类型创建复合控件从 UserControl 类。

创建 windows 窗体组合控件

  1. 在 Visual Basic 中添加个新的 windows 窗体控件库名为 VendorControlLibrary 的项目或 Visual c# 为解决方案。 有关更多信息,请参见 How to: Add and Remove Solution Items

    UserControl1 在 windows 窗体设计器中打开。

  2. 解决方案资源管理器,右击 UserControl1 文件,然后选择 重命名

  3. 该控件的名称更改为 VendorControl。 当系统询问是否重命名所有引用时,单击

  4. 在设计图面上,选择 VendorControl。

  5. 属性 窗口中,将 Size 属性的值设置为 200,200。

  6. 工具箱,双击 MonthCalendar 控件。

    MonthCalendar 控件随即出现在设计图面上。

  7. 属性 窗口中,将 MonthCalendar 控件的以下属性。

    属性

    value

    页边距

    0,0,0,0

    ShowToday

    FALSE

  8. 将 VendorControl 的大小匹配 MonthCalendar 控件的大小。

  9. 选择 MonthCalendar 控件。

  10. 在 " 属性 " 窗口中,单击 " 事件 " 选项卡并双击 DateChanged 事件。

    在代码编辑器中打开 VendorControl 文件,并且, DateChanged 事件的事件处理程序添加到中。

  11. 用下面的代码替换现有代码。 此代码定义一个 Date 属性和一些逻辑限制的 MonthCalendar 控件的日期范围属性, SelectionStartSelectionEnd,该值和 TodayDate相同。 此代码还实现 INotifyPropertyChanged 接口,用于 WPF 数据绑定。

    Imports System
    Imports System.Collections.Generic
    Imports System.ComponentModel
    Imports System.Drawing
    Imports System.Data
    Imports System.Linq
    Imports System.Text
    Imports System.Windows.Forms
    
    Public Class VendorControl
        Inherits UserControl
        Implements INotifyPropertyChanged
    
        <Browsable(True)> _
        Public Property [Date]() As String
            Get
                Return Me.MonthCalendar1.TodayDate.ToShortDateString()
            End Get
    
            Set(ByVal value As String)
                If value <> Me.MonthCalendar1.TodayDate.ToShortDateString() Then
                    Dim newDate As DateTime = DateTime.Parse(value)
                    Me.SetDate(newDate)
                    Me.NotifyPropertyChanged("Date")
                End If
            End Set
        End Property
    
    
        Private Sub monthCalendar1_DateChanged( _
            ByVal sender As Object, ByVal e As DateRangeEventArgs) _
        Handles MonthCalendar1.DateChanged
            Me.SetDate(e.Start)
            Me.NotifyPropertyChanged("Date")
    
        End Sub
    
    
        Private Sub SetDate(ByVal [date] As DateTime)
            Me.MonthCalendar1.TodayDate = [date]
            Me.MonthCalendar1.SelectionStart = [date]
            Me.MonthCalendar1.SelectionEnd = [date]
    
        End Sub
    
    #Region "INotifyPropertyChanged Implementation"
    
        Public Event PropertyChanged As PropertyChangedEventHandler _
            Implements INotifyPropertyChanged.PropertyChanged
    
        Private Sub NotifyPropertyChanged(ByVal info As String)
            RaiseEvent PropertyChanged(Me, New PropertyChangedEventArgs(info))
        End Sub
    
    #End Region
    End Class
    
    using System;
    using System.Collections.Generic;
    using System.ComponentModel;
    using System.Drawing;
    using System.Data;
    using System.Linq;
    using System.Text;
    using System.Windows.Forms;
    
    namespace VendorControlLibrary
    {
        public partial class VendorControl : UserControl, INotifyPropertyChanged
        {
            public VendorControl()
            {
                InitializeComponent();
            }
    
            [Browsable(true)]
            public string Date
            {
                get
                {
                    return this.monthCalendar1.TodayDate.ToShortDateString();
                }
    
                set
                {
                    if (value != this.monthCalendar1.TodayDate.ToShortDateString())
                    {
                        DateTime newDate = DateTime.Parse(value);
                        this.SetDate(newDate);
                        this.OnPropertyChanged("Date");
                    }
                }
            }
    
            private void monthCalendar1_DateChanged(object sender, DateRangeEventArgs e)
            {
                this.SetDate(e.Start);
                this.OnPropertyChanged("Date");
            }
    
            private void SetDate(DateTime date)
            {
                this.monthCalendar1.TodayDate = date;
                this.monthCalendar1.SelectionStart = date;
                this.monthCalendar1.SelectionEnd = date;
            }
    
            #region INotifyPropertyChanged Implementation
    
            public event PropertyChangedEventHandler PropertyChanged;
    
            private void OnPropertyChanged(string propertyName)
            {
                if (this.PropertyChanged != null)
                {
                    this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
                }
            }
    
            #endregion
        }
    }
    
  12. 生成 菜单中,选择 生成解决方案 生成解决方案。

在 WPF 中承载 windows 窗体控件

使用 WindowsFormsHost 元素在 WPF 应用程序中承载 VendorControl。

在 WPF 中承载 windows 窗体控件

  1. 解决方案资源管理器HostingMonthCalendar 项目中,添加对 VendorControlLibrary 项目。 有关更多信息,请参见 如何:添加或移除引用使用 " 添加引用 " 对话框

  2. 打开在 WPF Designer的 MainWindow.xaml。

  3. 工具箱,请拖动到设计图面的一个 WindowsFormsHost 控件图面。

    对名为 WindowsFormsIntegration.dll 的程序集的引用添加到 HostingMonthCalendar 项目。

  4. 在 XAML 视图中,用以下标记替换现有标记。 此 XAML 命名空间映射 VendorControlLibrary 并将 TextBlock 元素对 VendorControl的 Date 属性。

    <Window x:Class="HostingMonthCalendar.MainWindow"
        xmlns="https://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="https://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:v="clr-namespace:VendorControlLibrary;assembly=VendorControlLibrary"
        Title="Window1" Height="300" Width="300">
        <Grid>
            <Grid.RowDefinitions>
                <RowDefinition Height="Auto" />
                <RowDefinition />
            </Grid.RowDefinitions>
    
            <WindowsFormsHost Name="Host" Grid.Row="0" HorizontalAlignment="Center" VerticalAlignment="Center">
                <v:VendorControl Date="2/2/03" />
            </WindowsFormsHost>
    
            <TextBlock Grid.Row="1" 
                       Text="{Binding ElementName=Host, Path=Child.Date, Mode=OneWay, UpdateSourceTrigger=PropertyChanged }" 
                       HorizontalAlignment="Stretch" 
                       VerticalAlignment="Center" 
                       TextAlignment="Center" 
                       TextDecorations="None" 
                       FontSize="24" />
        </Grid>
    </Window>
    
  5. 调试 菜单中,选择 启动调试

  6. 单击 MonthCalendar 控件以更改当前日期。 显示所选日期的 WPF TextBlock 元素更新。

后续步骤

  • 如果控件将在 WPF 环境中广泛使用,可以从 WindowsFormsHost 派生您的类并显示 Date 属性。 这使得其他 WPF 控件可以直接绑定到属性, Date ,而无需使用 Path=Child.Date 语法。

  • 还可以在 windows 窗体中承载 WPF 控件。 有关更多信息,请参见 使用 WPF 控件

请参见

任务

演练:在 WPF 中承载 Windows 窗体控件

参考

WindowsFormsHost

ElementHost

其他资源

使用 WPF 设计器中的控件

迁移和互操作性