4

背景

我正在将 SourceForge 上的 TreeViewAdv(TVA) 项目转换为 vb.net。到目前为止,我已经成功地转换了代码,成功地构建了它,将 dll 的引用添加到了新项目中,将控件添加到了工具箱中,将控件添加到了窗体中,并修改了控件的属性。在构建接受 Aga.Controls 命名空间之前,我还将功能编码到表单中。

问题

当我去调试已放置 TVA 控件的应用程序时,我收到错误消息:' 'Aga' 未声明。由于其保护级别,它可能无法访问。' 对该命名空间的所有调用。所以,我在 SourceForge 上研究了这个问题,这里有一个线程:https ://sourceforge.net/p/treeviewadv/discussion/568369/thread/005e61ef/讨论了这个问题。据说有人在您看到这样的行为时发现了问题所在,但未能分享他们智慧的任何细节。一般的问题是,当在 2010 项目中引用 2008 年编译的 dll 时,“VS 2010 要求您将设计器与主程序集分开。” 我尝试联系那里的人,但论坛中的任何线程似乎都没有真正的活动。这引出了我的第一个问题......

问题

1.)希望超出希望,StackOverflow 上是否有人专门为 treeviewadv 项目成功完成了这项工作?如果是这样,我真的很感激对所做工作的详细描述,或者对最终生成的代码/修复的简短描述。虽然我知道这不太可能,但我想在询问有关“如何”的更一般性问题之前先问一下?

2.) 除非任何人符合 1 号的要求,是否有任何人了解这个一般过程,并且至少对 TVA 项目有足够的了解,并希望与我一起努力完成这项工作?

2.)除 1 和 2 之外,是否有人在任何项目中完成了此操作,并且可以相对详细地描述一般过程和/或指向示例代码?

3.) 除了 1、2 和 3,我是否可以访问一个特别好的资源,其中概述了如何以上述方式更新 VS2008 项目?

免责声明

我知道这个过程可能过于复杂,无法在这里讨论,因此如果需要,我愿意在其他地方进行讨论/努力。如果第 1 类或第 2 类的人可以(回答我的问题/与我一起工作)并且您认为应该在其他地方进行讨论,请告知我我们如何相互联系,因为似乎没有关于 SO 的正式机制。如果可以找到答案,我仍然有兴趣在此处发布(或链接)结果以供所有人分享。

4

2 回答 2

1

这里有更多信息解决设计器在不同程序集中的一般问题。有一些警告:首先我(我们?)不确定与UI设计师有关的核心问题。鉴于该项目似乎是一个自定义 TreeView,它似乎很可能是这种情况,但术语“设计器”可以以更通用的方式用于此控件。第二个警告是,我所要做的只是上面的描述,还没有看到控件的代码。

也就是说,我刚刚完成了撤消管理器组件(即它继承自 Component 并位于表单托盘中)。它需要的一部分是开发人员选择表单上的控件以进行撤消的方法。布局/构造是这样的:

Imports Plutonix.UIDesigners

Namespace Plutonix.UnDoMgr

Public Class UndoManager
    Inherits Component      
    Implements ISupportInitialize      

    Private _TgtControls As New Collection(Of Control)

    <EditorAttribute(GetType(UnDoControlCollectionUIEditor), _
          GetType(System.Drawing.Design.UITypeEditor))> _
    <DesignerSerializationVisibility(DesignerSerializationVisibility.Content)> _
    Public Property UnDoTargets() As Collection(Of Control)
        Get
            Return _TgtControls
        End Get
        Set(ByVal value As Collection(Of Control))
            If value IsNot Nothing Then
                _TgtControls = value
            Else
                _TgtControls.Clear()
            End If
        End Set
    End Property
    '...

<EditorAttribute...装饰指定此组件使用一个名为 的特殊设计器UnDoControlCollectionUIEditor。如果您正在转换的项目在一个或多个属性上没有此属性,则该问题可能与UI设计人员无关。

稍后,还有用于 CControls 集合编辑器的 UI 编辑器。这是一个单独的类,尽管它在同一个文件中:

  <System.Security.Permissions.PermissionSetAttribute( _
        System.Security.Permissions.SecurityAction.Demand, Name:="FullTrust")> _
Public Class UnDoControlCollectionUIEditor
    Inherits ControlCollectionUIEditor

    Public Sub New()
        MyBase.bExcludeForm = True
        MyBase.bExcludeSelf = True

       ' create a list of supported control TYPES
        typeList.Add(GetType(TextBox))
        '... 9 more lines adding control types to List(of System.Type)
    End Sub
 End Class

几乎所有代码都驻留在ControlCollectionUIEditor不同程序集(DLL)中的基类中。虽然我的组件实际上使用的是本地定义的,但作为测试,我将编辑器更改为使用ControlCollectionUIEditor哪个是我的设计器 DLL 中的基类。标签、面板、GroupBoxes 等没有/不需要撤消功能,因此我的设计器使它们免于在设计器中显示 - 当我使用基类时,它们都按预期显示在设计器列表中。

所有标准 UI 编辑器(字符串集合编辑器等)都在 NET 程序集中,因此在一个程序集中定义并在另一个程序集中使用(您的/我们的/开发人员)。几年前,我决定将我编写的几个不同的 UIDesigner 放入 UIDesigner.DLL(即它们自己的程序集)中,它们工作得很好。

除此之外,我对一些细节感到困惑。听起来您正试图在转换中使用这个 2008 程序集(DLL?)。是设计师所在的地方吗?如果是这样,它已经在您的 VS 2010 项目的另一个程序集中,那么为什么会出现问题?是否可以通过转换 2008 年大会中的任何内容来避免整个事情(仍然不清楚其中的内容)。

高温高压

编辑

我快速查看了源代码,它至少使用了 1 个 UIDesigner。 TreeViewAdv.Properties.cs定义NodeControlCollectionEditor为属性的自定义控件集合编辑器NodeControls。编辑器在NodeControlsCollection.cs. 巧合的是,它与我的 UnDoManager 所做的完全一样:定义哪些控件类型对 CollectionEditor 有效。然后你的东西调用标准的 NET CollectionEditor,我的调用 CodeProject DialogForm 版本。还有一个StringCollectionEditor.cs文件,但我不知道那是 UI 设计器还是运行时用户的东西。

既然你有这些代码,你应该能够模仿我上面所做的事情。我还将验证 VS 2010 确实有提到的怪癖。但我也对 2008 年大会的内容感到困惑。有没有你没有来源的作品?您也可以尝试将安全属性添加到项目中的任何 UI 设计器,因为 CS 版本没有它们,并且引用的 msg 表示有关“保护级别”的内容。这似乎不太可能有帮助,但既然你正在处理一个怪癖,谁知道......?

此外,这是一个非常雄心勃勃的转换项目!

于 2013-11-14T14:10:34.463 回答
0

问题原因已验证

首先,我想指出,确实,在引用的 dll 中丢失命名空间的问题是因为该 dll 中存在自定义 UI 编辑器/设计器。

修复

从“主要”类库中分离自定义编辑器/设计器的一般过程是这样的:

1.)找到项目中的所有自定义编辑器/设计器。如果您只是对该项目有点熟悉,那么一个好的方法是在整个解决方案中查找(Ctrl + F) 'UITypeEditor'。如果你是设计它的人,那么你应该没有问题。

2.)删除或注释掉整个自定义编辑器/设计器类。我更喜欢注释掉以方便文档(以防万一您需要返回)。

3.)在解决方案中创建新项目。如果您看不到解决方案(即您只能看到项目),请转到工具-->选项-->项目和解决方案。在那里,您将看到一个显示“始终显示解决方案”的复选框。显示解决方案后,右键单击并选择 add-->New Project... 可以任意命名,这对代码几乎没有影响。

4.)在新项目中将 Class1 重命名为方便的名称。在最初保存自定义编辑器/设计器类的文件顶部传输所有“使用”语句。 编辑:为允许您从主项目访问所需类型的任何命名空间添加 using 语句。为每个类声明适当的命名空间。将自定义类复制并粘贴到正确的命名空间中(如果需要,您可以将所有自定义编辑器/设计器放在这个文件中)。将任何声明为“内部”的类更改为“公共”(内部只是程序集的范围)。

5.)如果新项目需要任何引用,请立即添加。如果您的自定义编辑器正在编辑自定义类型,您可能需要对定义这些类型的项目的引用。如果这些类型是在您的“主要”程序集中定义的,这可能会有点棘手,因为它可能会导致循环引用问题。解决此问题的一种方法(可能也是正确的方法)是从主程序集中删除这些类型的声明,并仅为它们的声明创建一个新项目/程序集。如果由于某种原因它们与您的主程序集密不可分,请搁置先前由您的主程序集制作的成功构建 (dll) 并引用它。这会降低代码的未来可持续性,因为这些类型可能会发生,但如果这是您想要的,现在就可以完成工作。

6.)在调试自定义编辑器/设计器项目后,构建它并将该项目的构建 (dll) 作为参考添加到主项目/程序集中。

7.)内部调试,在解决方案中创建一个新项目并将两个dll(主编辑器和自定义编辑器)添加到引用中。验证控件/属性在设计时和运行时的行为是否符合预期。

8.)最后,在外部 调试。创建新的解决方案,引用两个 dll,验证功能。在本机解决方案和外部进行调试似乎有点矫枉过正,但我​​发现环境之间的行为存在许多差异。要彻底。

重要提示: 我花了很长时间才确定需要添加两个 dll。您会看到,当仅将主 dll 添加到测试项目时,它的行为就像同时添加了两者一样。我虽然这是合理的(而且相当花哨),因为主程序集引用了另一个程序集。但是,关闭并打开 Visual Studio,它不起作用。长话短说添加两个 dll。

TreeViewAdv 细节

1.)有两个自定义 UIEditor。第一个是在 NodeControlsCollection.cs 中称为 NodeControlCollectionEditor,它继承了标准的 .NET CollectionEditor。添加的唯一功能是明确分配允许编辑器使用的控件类型。似乎这在很大程度上是作为一种解决方法来允许将所有 NodeControl 类型添加到集合中(这需要传递类型 NodeControl),但是绕过传递 NodeControl 类型会导致错误的事实,因为您无法实例化抽象类型. 第二个是StringCollectionEditor.cs 中的StringCollectionEditor。这也继承了标准的 .NET CollectionEditor 并添加了一些功能(不确定目的)。

2 - 4.)与一般过程相同。

5.) 我目前不得不使用后一种方法(留出 Aga.Controls 的 dll 供我的自定义 UIEditor 参考)。稍后我希望将一些对象声明与主程序集分开,以使解决方案更可靠。

6 - 8.) 在同一个解决方案(即使是不同的项目)中运行测试应用程序时,不会发生原始错误(丢失 aga 命名空间)。此外,一些在外部工作的修复程序在内部没有正确运行,反之亦然。因此,我建议在这两种环境中进行测试。

最终请求 虽然我的问题的一般性和细节性都在这里得到了解答,但 Plutonix 的帮助对于我找到解决方案至关重要。虽然我将此标记为答案。我想如果人们也支持 Plutonix 的答案,因为他为帮助我找到答案所付出的努力(此外,如果他的答案不太具体,他的答案也是正确的)。

编辑:当我修改原始 TVA C# 代码时,上述过程有效。我什至能够在 VB.net 项目中引用并成功使用生成的 DLL。当我尝试将相同的过程应用于已转换为 VB.net 的 TVA 代码行时,它导致了与我开始时相同的问题。一切正常,直到我去运行应用程序,然后它看不到 aga 命名空间。

编辑解决方案: 转到属性(项目丢失参考)--> 编译选项卡--> 高级编译选项按钮。在目标框架下,如果还没有,请更改为“.NET Framework 4”。如果已选择该值,则您可能正在寻找不同的原因。

于 2013-11-16T23:35:46.107 回答