一直使用这个方法进行视图的动态创建,从没遇到过问题。今天需要从一继承自CView的视图类创建。结果遇到失败!!!
这里的pViewClass就是你想创建的视图类用法如下:
CChildFrame* pChildFrame = (CChildFrame*)CreateNewView(IDR_MAINFRAME,RUNTIME_CLASS(CChildFrame),
RUNTIME_CLASS(CView),pDocument);
这里只要我使用RUNTIME_CLASS(CView)就失败,或者自己从CView继承的类也是失败,如果换做其他的比如CListView或者子类,都没有问题。唯独CView遇到问题,我很纳闷,跟踪无果,再说其他CListView最终也是继承自CView的啊。大家帮忙看看,谢谢了。CMDIChildWndEx* CMainFrame::CreateNewView(UINT nIDResource, CRuntimeClass *pFrameClass, CRuntimeClass *pViewClass, CDocument *pDoc)
{
CMDIChildWndEx* pFrame=(CMDIChildWndEx*)pFrameClass->CreateObject();
ASSERT_KINDOF(CMDIChildWndEx, pFrame); CCreateContext context;
context.m_pCurrentDoc=pDoc; // use existing document
context.m_pCurrentFrame=NULL; //pFrame;// new child frame to be upon
context.m_pNewViewClass=pViewClass; // RUNTIME_CLASS(CMyHtmlView);// new view to be created
context.m_pNewDocTemplate=pDoc->GetDocTemplate(); //pTemplate;// use existing document template
context.m_pLastView=NULL; // no  if (!pFrame->LoadFrame(nIDResource,WS_OVERLAPPEDWINDOW|FWS_ADDTOTITLE,/*AfxGetMainWnd()*/this,&context)) 
{
TRACE(L"Warning: Couldn't load frame window!\n");
AfxMessageBox(_T("Warning: Couldn't load frame window!\n"));
return NULL;
} pFrame->InitialUpdateFrame(pDoc,TRUE);
//just delagate to implementation in CFrameWnd
//pTemplate->InitialUpdateFrame(pHtmlChild,pDoc,TRUE); //it worked!
return pFrame;
}

解决方案 »

  1.   

    创建View失败?什么意思?程序崩溃了还是怎么了?
      

  2.   

    Error: Trying to create object which is not DECLARE_DYNCREATE 
    or DECLARE_SERIAL: CView.
    Error: Trying to create object which is not DECLARE_DYNCREATE 
    or DECLARE_SERIAL: CView.这不有个错误提示吗
      

  3.   

    显然CView设计时就不支持动态创建
      

  4.   

    查看MFC源码
    CListView 就支持动态创建
    afxcview.hclass CListView : public CCtrlView
    {
    DECLARE_DYNCREATE(CListView)CView 就不支持
    afxwin.hclass CView : public CWnd
    {
    DECLARE_DYNAMIC(CView)
      

  5.   

    pFrame->LoadFrame()返回失败了。
      

  6.   

    CCreateContext cc;
    cc.m_pCurrentDoc = NULL;
    cc.m_pCurrentFrame = this;
    cc.m_pLastView = NULL;
    cc.m_pNewDocTemplate = NULL;
    cc.m_pNewViewClass = RUNTIME_CLASS(CMyVView); CView *m_pviewLogin = (CView*)this->CreateView(&cc);
    if(m_pviewLogin == NULL)
    {
    TRACE("CreateView failed!\n");
    return -1;
    }
    m_pviewLogin->ModifyStyleEx(WS_EX_CLIENTEDGE,NULL);
    class CMyVView : public CView
    {
    DECLARE_DYNCREATE(CMyVView)protected:
    CMyVView();           // 动态创建所使用的受保护的构造函数
    virtual ~CMyVView();public:
    virtual void OnDraw(CDC* pDC);      // 重写以绘制该视图
    #ifdef _DEBUG
    virtual void AssertValid() const;
    #ifndef _WIN32_WCE
    virtual void Dump(CDumpContext& dc) const;
    #endif
    #endifprotected:
    DECLARE_MESSAGE_MAP()
    };
    不知道你是怎么做的,反正我随便继承个CView,如此创建就成功了
      

  7.   

    不太一样,我就是直接在FrameWnd里创建了一个View,没用文档也没用模板
      

  8.   

    怪事,好像是有问题。我刚到家新建一个工程,从CView派生一个CMyView,用这个方法居然是成功的。
    我产品的工程好像有问题,一定是我别的地方有问题。看来麻烦大了当初为了研究我的这个CreateNewView()方法,深入的研读了MFC SRC代码,追踪了MFC VIEW/DOC的机制。当时确信这个方法应该是没有问题的了,今天突然懵了MDI工程,针对同一个文档的多视图创建,比如一个CView、CListView、CChartView,大家都是如何实现同一个数据源的多视图展示?有否别的方法分享?谢谢。
      

  9.   

    多谢。我刚测试了一番,好像找到些问题。有可能是我创建新视图的引用#include出现问题了。
    CMyView里面又引用了该视图视图使用的框架类头文件,导致无法预知的引用错误,可能如此。
    正在修改测试。MFC的文档视图架构实在太复杂,MFC的封装也很是难于理解。我当初花费了3个月的时间研读MFC SRC关于DOC/VIEW部分的实现框架,基本上还比较清楚,也很佩服MFC的源代码的优雅。
      

  10.   

    我之前写的动态创建的就可以,今天突然不可以了,请问teleinfor或者其它朋友,你发现的是怎么个冲突法?
    我是用vs2008做的mfc程序,将模板定义修改为:
    CMultiDocTemplate* pDocTemplate;
    pDocTemplate = new CMultiDocTemplate(IDR_MAINFRAME,
    RUNTIME_CLASS(CVAppExeDoc),
    RUNTIME_CLASS(CChildFrame), // 自定义 MDI 子框架
    RUNTIME_CLASS(CVAppExeView));
    进行了屏蔽系统自身菜单,加载自定义菜单,做了不少工作,后面也成功了。
    动态创建是通过一个命令调用一个dll,这个dll再发消息到mainframe进行创建,
    创建代码如下:
    CChildFrame* pFrame = new CChildFrame;
    CCreateContext Context;
    CVAppExeDoc* pMsgsManagerDoc = (CVAppExeDoc*)(RUNTIME_CLASS(CVAppExeDoc)->CreateObject());
    Context.m_pCurrentDoc = pMsgsManagerDoc ;
    Context.m_pLastView  = NULL;
    Context.m_pNewDocTemplate = NULL;
    Context.m_pCurrentFrame = this;
      POSITION pos = theApp.m_pDocManager->GetFirstDocTemplatePosition();
      Context.m_pNewDocTemplate = theApp.m_pDocManager->GetNextDocTemplate(pos);

    Context.m_pNewViewClass = RUNTIME_CLASS(CVAppExeView); pFrame->LoadFrame(IDR_MAINFRAME, WS_OVERLAPPEDWINDOW | WS_CAPTION | FWS_ADDTOTITLE, this, &Context ); CVAppExeView* pView = (CVAppExeView*)(Context.m_pLastView);
    ASSERT(pView);然后就在ASSERT(pView);出现断言,
    有朋友可以帮忙看下吗?