为什么在向表单添加控件后,Visual C ++ Designer无法正常工作?

时间:2012-06-01 16:18:26

标签: .net winforms visual-studio-2008 visual-c++

我想在面板中打开双缓冲,但我们唯一可以启用DoubleBuffered属性的方法是创建一个继承自System::Windows::Form::Panel的新类,如下所示:< / p>

#include "stdafx.h"

public ref class CPPIConfig: public System::Windows::Forms::Panel
{
public: CPPIConfig()
        {
            this->DoubleBuffered = true;
        }
};

我们的表单现在看起来像这样:

#pragma once
#using <system.drawing.dll>
#include "CPPIConfig.h"

[...]

public ref class C3_User_Interface : public System::Windows::Forms::Form
    {
      [...]
      public: CPPIConfig^ pPPI;
      [...]
    }

void InitializeComponent(void)
    {
        [...]
        this->pPPI = (gcnew CPPIConfig());
        [...]
    }
[...]

它构建并运行,没问题。但是,当我尝试在设计模式下查看表单时,我收到以下错误:

  

C ++ CodeDOM解析器错误:行:144,列:15 ---未知类型'CPPIConfig'。请确保引用包含此类型的程序集。如果此类型是开发项目的一部分,请确保已成功构建项目。

我的问题:

  1. 为什么设计模式不起作用,即使代码构建和运行?我已经尝试了几个干净的版本,但这看起来不是问题。
  2. 我可以在不使用此方法的情况下将DoubleBuffered设置为true吗?

3 个答案:

答案 0 :(得分:4)

这里的大麻烦真的源于我的托管代码与非托管代码的混合。我去了MSDN to read more about it,但结果是: Visual Studio无法在此上下文中处理我的CPPIConfig类,因为它是非托管/本机代码。

similar question提供的答案:

  

Windows窗体设计器无法反映混合模式的EXE。确保使用/ clr:pure编译或将任何需要设计时支持的类(例如表单上的组件和控件)移动到类库项目。

Reflection,as this MSDN page points out是Design视图用于在IDE中呈现Form的内容。简而言之,这就是反思:

  

Reflection允许在运行时检查已知数据类型。 Reflection允许枚举给定程序集中的数据类型,并且可以发现给定类或值类型的成员。无论类型是在编译时是已知还是引用,都是如此。这使得反射成为开发和代码管理工具的有用功能。

稀释。这开始有意义了。

据我所知,有两种方法可以解决这个问题。

在项目属性中使用/clr:pure这会更改项目的公共语言运行时支持。来自this MSDN page:

  

纯程序集(使用/ clr:pure编译)可以包含本机和托管数据类型,但只包含托管函数。与混合程序集一样,纯程序集允许通过P / Invoke与本机DLL互操作(请参阅在C ++中使用显式PInvoke(DllImport属性)),但C ++ Interop功能不可用。此外,纯程序集无法导出可从本机函数调用的函数,因为纯程序集中的入口点使用__clrcall调用约定。

创建一个类库项目。正如另一个答案建议的那样,如果我将文件移动到类库项目并以这种方式引用它,我就不会看到这个问题。据我了解,它会使CPPIConfig托管代码。

最终,结构限制使得这些选项都不可行,并且为了时间的推移,我们决定暂时放弃面板上的双重缓冲。哦,至少我对这个环境有了更多的了解!

答案 1 :(得分:1)

尝试将控件初始化移动到suspendlayout下方。这允许设计者在没有CodeDOM解析错误的情况下正确呈现。

原创就像是

#pragma region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
void InitializeComponent(void)
{
    this->lblMessage = (gcnew System::Windows::Forms::Label());
    this->SuspendLayout();
    // lblMessage
    this->lblMessage->Location = System::Drawing::Point(12, 230);
    //.....
}

新格式

#pragma region Windows Form Designer generated code
/// <summary>
/// Required method for Designer support - do not modify
/// the contents of this method with the code editor.
/// </summary>
void InitializeComponent(void)
{
    this->SuspendLayout();
    // lblMessage
    this->lblMessage = (gcnew System::Windows::Forms::Label());
    this->lblMessage->Location = System::Drawing::Point(12, 230);
    //.....
}

答案 2 :(得分:0)