【问题标题】:Getting the assembly a control is being used in, from a custom UITypeEditor, at design time在设计时从自定义 UITypeEditor 获取正在使用控件的程序集
【发布时间】:2017-05-08 16:20:57
【问题描述】:

虽然有很多线程处理类似的问题,但我找不到任何涉及这种情况的线程。

我有一个引用类库的主应用程序。在类库中是一个具有属性的控件,该属性必须从主应用程序中可用的表单下拉列表中填充表单名称 - 而不是类库。

我发现,在 UITypeEditor 代码中,

Control owner = context.Instance as Control;

给我一​​个对需要属性值的控件的引用。但是要获得对正确程序集(主应用程序,而不是控件所在的库)的引用,以便我可以在下拉列表中列出可用的表单名称,这被证明是困难的。

owner.GetType().Assembly.ToString() -- 给我类库名称,而不是主应用程序

Assembly.GetExecutingAssembly().ToString() --- 给我类库名称

Assembly.GetCallingAssembly().ToString() --- 给我 System.Windows.Forms

我找不到任何方法来获取我要放置控件的表单的程序集,该控件具有需要该程序集的自定义编辑器的属性。

【问题讨论】:

    标签: uitypeeditor


    【解决方案1】:

    我意识到这是一个老问题,但如果了解编写基本设计器代码所采用的机制,则很容易回答。我建议您阅读三篇文章,以获取有关该主题的实用知识。

    1. 构建具有丰富设计时功能的 Windows 窗体控件和组件; MSDN Magazine, April 2003
    2. 构建具有丰富设计时功能的 Windows 窗体控件和组件,第 2 部分; MSDN Magazine, May 2003
    3. 通过使用 .NET 构建自定义表单设计器来定制您的应用程序; MSDN Magazine, December 2004

    注意:以上链接指向已编译的 HTML 帮助文件。请记住使用文件的属性对话框取消阻止内容。

    要获得对包含FormAssembly 的引用,并且在设计图面上对Control 进行操作,您需要从IDesignerHost 服务的引用获得IServiceProvider 实例“提供程序”的引用" 即通过 EditValue 方法。 IDesignerHost 公开属性RootComponentClassName,它将是基组件类的完全限定名称,在这种情况下是包含表单。使用此名称,您可以使用IDesignerHost.GetType 方法获取Type 实例。请注意,如果在将表单添加到项目后尚未“构建”项目,GetType 可能会返回空值。

    UITypeEditor 的 C# 示例代码段

    public override object EditValue(System.ComponentModel.ITypeDescriptorContext context, IServiceProvider provider, object value)
        {
        IDesignerHost host = provider.GetService(typeof(IDesignerHost)) as IDesignerHost;
        string typName = host.RootComponentClassName;
        Type typ = host.GetType(typName);
        Assembly asm = null;
        if (typ == null)
            {
            MessageBox.Show("Please build project before attempting to set this property");
            return base.EditValue(context, provider, value);
            }
        else
            {
            asm = typ.Assembly;    
            }
        // ... remaining code
    
        return base.EditValue(context, provider, value);
        }
    

    用于 UITypeEditor 的 VB 示例代码段

    Public Overrides Function EditValue(context As ITypeDescriptorContext, provider As IServiceProvider, value As Object) As Object
        Dim host As IDesignerHost = TryCast(provider.GetService(GetType(IDesignerHost)), IDesignerHost)
        Dim typName As String = host.RootComponentClassName
        Dim typ As Type = host.GetType(typName)
        Dim asm As Assembly
        If typ Is Nothing Then
            MessageBox.Show("Please build project before attempting to set this property")
            Return MyBase.EditValue(context, provider, value)
        Else
            asm = typ.Assembly
        End If
        ' ... remaining code
    
        Return MyBase.EditValue(context, provider, value)
    End Function
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2013-04-05
      • 1970-01-01
      • 2013-03-04
      • 2021-11-28
      • 2011-12-07
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多