我自己做了一个MyToolBar的类,把它封装在一个DLL中,在DLL中导出一个显示函数DisplayMyToolBar(CFrameWnd *hWnd),函数定义是
BOOL DisplayMyToolBar(CFrameWnd *hWnd)
{
MyToolBar  m_wndMyToolBar; //创建MyToolBar 
if (!m_wndMyToolBar .Create(_T("记录列表"), hWnd, 123))
    {
        TRACE0("Failed to create CoolBar\n");
        return -1;      // fail to create
} m_wndMyToolBar .EnableDocking(CBRS_ALIGN_ANY);
DockControlBar(&m_wndMyToolBar , AFX_IDW_DOCKBAR_LEFT); return TRUE;
}其中函数参数CFrameWnd *hWnd的类型本来是想CMainFrame类的,结果发现此类在创建主程序是才会派生出来,而在DLL中根本没有,所以不能使用。然后在新建的主应用程序中的CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct)函数中,加入DisplayMyToolBar(this)语句(加在这里主要是因为主程序的工具栏和状态栏的加载都在这里,就照做了)。this指针的用法也和主程序的工具栏状态栏的使用是一样的。   现在问题来了,把DLL和主程序都编译通过,DLL和主程序的链接也无问题,可是在运行主程序的可执行文件时出错,让你终止、重试或忽略。   我估计就是涉及到的两个指针不一样的问题。一个是CFrameWnd,一个是CMainFrame,可是这个CMainFrame的指针到底应该如何传递,在DLL中又应该如何定义,这个我就不清楚了。所以请各位高手帮忙解答一下。谢谢!!!

解决方案 »

  1.   

    你的MyToolBar是个临时变量,函数返回之后就析构了,不是指针的问题。
      

  2.   

    MyToolBar  m_wndMyToolBar;
    应该加在CMainFrame的定义中,即做为CMainFrame的成员变量,
    要不然用
    static MyToolBar m_wndMyToolBar;
      

  3.   

    同意 dizzo(牛说:别哭,要坚强!)的说法:改成
     MyToolBar* p_wndMyToolBar = new MyToolBar; 记得要释放!
     delete p_wndMyToolBar;
      

  4.   

    修改了代码后又出现新的问题。我将MyToolBar的类,在应用程序的MainFrame类里声明了一个成员变量MyToolBar *m_wndMyToolBar,然后将此变量的指针传递给在DLL中导出的显示函数DisplayMyToolBar(CFrameWnd *hWnd,MyToolBar *m_wndMyToolBar),函数定义是
    BOOL DisplayMyToolBar(CFrameWnd *hWnd,MyToolBar *m_wndMyToolBar)
    { //创建MyToolBar 
    if (!m_wndMyToolBar .Create(_T("记录列表"), hWnd, 123))
        {
            TRACE0("Failed to create CoolBar\n");
            return -1;      // fail to create
    } m_wndMyToolBar .EnableDocking(CBRS_ALIGN_ANY);
    DockControlBar(&m_wndMyToolBar , AFX_IDW_DOCKBAR_LEFT); return TRUE;
    }本以为这样就可以了,结果刚运行程序,就弹出了程序错误,将被关闭的提示框。设了断点后,发现问题出在m_wndMyToolBar .Create(_T("记录列表"), hWnd, 123)上,到了这句就运行不下去了,提示什么访问违例之类的话。请有经验的高手帮忙看看问题出在什么地方,谢谢。
      

  5.   

    把CFrameWnd *hWnd,MyToolBar *m_wndMyToolBar替换成指针的指针就是CFrameWnd **hWnd,MyToolBar **m_wndMyToolBar试试看
      

  6.   

    没有分配内存
    在CMainFrame中先
    MyToolBar *m_wndMyToolBar;
    m_wndMyToolBar = new MyToolBar;
    再调用DisplayMyToolBar函数
    记得最后delete m_wndMyToolBar;
      

  7.   

    不过你这么作的话要动态连接库就没有意义了,如果你这个toolbar只创建一个的话,建议把MyToolBar  m_wndMyToolBar;声明为dll中的全局变量
      

  8.   

    是吗?谢谢。 声明成DLL中的全局变量是不是就不用在主程序中分配内存了呢?
      

  9.   

    我按照(累)的方法试了,结果编译时通不过,显示MyToolBar里的虚函数错误,提示:unresolved external symbol 。这是什么原因呢?
      

  10.   

    你的MyToolBar类实在dll中定义的吧,应该先导入后再使用
      

  11.   

    是的,MyToolBar类是封装在DLL里的,但是用AFX_EXT_CLASS导出了。而且主程序也隐式链接了dll,不知道还有什么地方不对。
      

  12.   

    还需要在主程序中用AFX_EXT_CLASS将类导入
      

  13.   

    确实我编程中都是只导出类,然后在主程序中include头文件就可以了,没有用过AFX_EXT_CALSS导入过,不过我发现这样子的话好象其它的类没有出现这种现象呀。我的主程序中的View和Doc类也一样都用dll里的类替换了,没出现问题呀。
      

  14.   

    我试了一下,在MainFrame类include “MyToolBar.h”语句后,加入了class AFX_EXT_CLASS MyToolBar;的语句,结果还是一样的。可能不是这个原因。
      

  15.   

    你没有将 CSizingControlBarG导出导致link错误,解决办法是在你的
    CSCBButton
    CSCBDockBar
    CSizingControlBar
    CSizingControlBarG
    四个类的声明中统统加上AFX_EXT_CLASS,并在CMainFrame实现文件中加上
    #pragma comment(lib,"ReportDLL.lib")还有,DisplayCoolBar函数显然是多余,你大可不必费此周章,你只需要在CMainFrame::OnCreate(...)中如下使用即可 m_wndCoolBar = new CCoolBar; //创建CoolBar
      if (!m_wndCoolBar->Create(_T("记录列表"), this, 123))
        {
            TRACE0("Failed to create CoolBar\n");
            return -1;      // fail to create
    }最后有一点小bug,如果你调用m_wndCoolBar->EnableDocking(CBRS_ALIGN_ANY);
    DockControlBar(m_wndCoolBar);的话会出现Debug Assertion Failure错误,因此需要将它删掉
      

  16.   

    最重要的是你居然没有释放资源,记得CMainFrame::~CMainFrame()
    {
    delete m_wndCoolBar;
    }
      

  17.   

    呵呵,我是个VC编程的新手呀,学VC刚3个月呢。以后还请 ukyoking(累)兄多多指教呀。 ^_^
      

  18.   

    DisplayCoolBar是因为我想在动态链接库里使用些编辑CoolBar的函数,可是我只知道从Dll中导出类,而不会往DLL中导入类,所以干脆就把CoolBar的所有操作都放在DLL中了。
      

  19.   

    http://www.eaoo.com/design/list.asp?classid=2&Nclassid=13
      

  20.   

    结贴了,都这么长时间了,谢谢大家的帮助。尤其是ukyoking(累)兄。