我有一个使用/ CLR编译的C ++'Control Library Project'。在这个项目中,有一个用户控件可以调用本机DLL。此用户控件应该出现在设计器工具箱中,但我无法将其拖到窗体上。如果没有对DLL的引用,用户控件可以正常使用,但是在引用时我只是在尝试使用它时收到消息“无法加载工具箱项”。
原生呼叫功能正常,无论如何都不会损害用户控制。通过包含DLL调用,可以在设计器中自行查看用户控件。此外,如果将控件手动添加到表单并作为程序执行,它也将显示正常。
这让我怀疑问题只是Visual Studio Designer需要知道本机DLL所在的位置。但我不知道如何告诉它,或者在哪里放置DLL以便它可以找到它。据我所知,在项目设置中没有办法引用本机DLL。所以对我来说,设计师只是抱怨是有道理的,因为它不能很好。
有没有办法让这项工作?
答案 0 :(得分:10)
不幸的是,您在VS 中遇到了“设计错误”(换句话说,就是“功能”)。
您怀疑问题是Visual Studio设计者需要知道本机DLL所在位置的问题部分正确。这不是对它的位置无知的问题,而是设计师无法反映混合模式程序集(包含托管代码和本机代码的程序集)以实例化控件的事实。这导致工具箱显示您记下的错误。
解决方法是使用/clr:pure
编译C ++源文件以创建纯粹管理的EXE。
另一种可能性(也就是VS中的“设计错误”)是您尝试添加的控件已编译为64位组件。因为Visual Studio是一个32位进程,所以它只能执行32位模块。虽然它允许您添加对64位程序集的引用,但它实际上无法JIT编译该64位程序集并在进程内执行它。
此处的解决方法是使用“AnyCPU”设置编译用户控件程序集,这将使其在32位环境中以32位进程执行,在64位中以64位进程执行环境。真的,假设你已经正确编写了代码,这是两全其美的。
最后,如果这些都不起作用,总会有绕过设计师的选择。您仍然可以编写实例化用户控件所需的代码,并在表单的初始化程序中设置其属性。您将失去的只是能够在Visual Studio中使用设计器内部的控件。一切都会在运行时按预期工作。
答案 1 :(得分:3)
使用/DELAYLOAD:"your_native.dll“选项链接您的库。这为我解决了同样的问题。
答案 2 :(得分:1)
我发现这看起来像一个类似的问题?
所以MS似乎正式表示从VS2008升级到VS2010作为解决方法。
您有没有找到不同的解决方法?
这是我在VS2008中使用C#.net托管项目时遇到的问题,该项目使用托管C ++包装器项目,使用非托管C ++项目。
我肯定认为Visual Studio正在使用的设计器临时程序集是一个问题 - 它将检测到的依赖包装程序集装入临时文件夹,但不包装那个包装程序集的非托管依赖项。我可以看到它在C:\ Users \ Username \ AppData \ Local \ Microsoft \ VisualStudio \ 9.0 \ ProjectAssemblies中。当我尝试加载设计器时,在其中创建了一个新文件夹,其中包含托管DLL但不是非托管依赖项。不幸的是,我无法理解上面微软链接中的问题中的人说的是使用$(TargetDir)的解决方法。
答案 3 :(得分:0)
要尝试的事情:
VS2010:将dll复制到Program Files\Microsoft Visual Studio 9.0\Common7\IDE\PublicAssemblies
文件夹。
VS2008,VS2010:将dll复制到AppData\Local\Microsoft\VisualStudio\<version>\ProjectAssemblies\
文件夹。
答案 4 :(得分:0)
在我看来,引用本机DLL的控件失败,因为Visual Studio无法加载它。尝试在运行时全局或为Visual Studio可执行文件设置PATH环境变量。如果这没有帮助,请尝试调试控件的设计时间行为,您应该能够找到问题。
答案 5 :(得分:0)
我遇到了类似的问题,可能与你的问题相同(谁知道有多少东西可能导致它?),基本上我无法将控制权交给设计师,但现有的控制工作正常生产和测试。
为了记录,这是我的解决方案:
1)将您的解决方案设置更改为x86。这让我可以控制设计师,移动它等等。 2)完成后,您可以返回AnyCPU或x64。我真的只是使用设计器来简化设置一些值,看起来整个32/64位的东西会导致问题。
答案 6 :(得分:0)
您可以在 .Net 中创建一个基类,并从该基类继承您的 cli 类。表单现在可以引用这个基类,而不是直接引用 cli 类型。它欺骗了设计师。