关于多个对话框控件共享ID的问题 和 DLL相关提问

Fireway2008 2008-10-24 08:15:42
本贴上接帖子《关于自编写的对话框类 及 对话框类与其资源分离的相关问题》
http://topic.csdn.net/u/20081010/15/c3b07ee4-bed3-4a3d-8ed1-d961d65f6d1a.html


各位程序设计的高手,
1. 本人原计划:写一个通用的CBaseDlg:public CDialog,并且它不与任何对话框资源绑定,在这个类里边添加一些对话框常用的 操作功能后,输出为DLL。
以后新添加的对话框如 ,假设新添加的对话框类名为CNewDlg,再引入CBaseDlg的DLL, 以 CNewDlg:pulic CBaseDlg的形式进行继承,之后在CNewDlg 里边添加新成员,绑定对话框资源和控件资源,结合CBaseDlg已有的函数和程序进行操作扩展,加大代码的重利用率。
之后发现,这样做好像不太行,除非这个类是Extend DLL的形式。
我所希望实现的是:做多个布局不同的对话框界面,但其上边的元素不变,只有控件的位置和布局改变而已。
2.为了实现原计划,本人有以下新的设想和提问:

设想一:
在Resource.h内,已经定义好了N多个控件的资源ID,他们都是与 COneDlg 绑定的对话框 IDD_ONE_DLG 里边的控件,
之后,我希望再添加几个新的对话框资源,并且 上边的控件ID 设定得和 COneDlg里边的一样,即ID共享。
因为我这几个对话框不会同时运行,一次只运行一个。


设想二:
利用MFC 的扩展 extend DLL ,写一个基础对话框类不和任何资源绑定 , 再让其他新的对话框类去继承他。但此法似乎有点复杂,资料也少



提问:
什么情况下才输出DLL呢?
像对话框之类的,如果全部集合在一个exe文件里边,和分开成为DLL分别调用,感觉在内存的利用也差不多的阿。
本人认为,如自写的控件类,特殊算法函数 ,全局钩子之类 可以输出为DLL调用,其他的就没太大必要。


不知道各位高手的看法如何?
...全文
286 25 打赏 收藏 转发到动态 举报
写回复
用AI写文章
25 条回复
切换为时间正序
请发表友善的回复…
发表回复
Fireway2008 2008-10-28
  • 打赏
  • 举报
回复
恩,看来用继承的方式也不太能达到理想效果,这和copy paste差不多的。

DLL内引入资源的方式和exe 情况下的差不多,区别在于定义类时候的输出头class __declspec(dllexport) C***Dlg

其他问题换个帖子提问,谢谢大家的帮助。
cnzdgs 2008-10-27
  • 打赏
  • 举报
回复
COneDlg内不能出现CSecondDlg的字样。
Fireway2008 2008-10-27
  • 打赏
  • 举报
回复
不好意思,有些地方打错字了,现在的工程里边只有
COneDlg、CSecondDlg、CMyDlg 这3个类和
IDD_ONE_DLG IDD_TWO_DLG 这2个对话框ID

COneDlg public: CMyDlg、CSecondDlg public:COneDlg

现在我就是打算在COneDlg内调用它的子类CSecondDlg的对象,能否实现呢?
Fireway2008 2008-10-26
  • 打赏
  • 举报
回复
我核对过了,没发现重复包含的地方,也许真是我的这种方式不够规范,于是我换了另一种方式:

即自写一个不绑定资源的对话框类CMyDlg
CMyDlg::CMyDlg(LPCTSTR lpszTemplateName, CWnd* pParentWnd)
: CDialog(lpszTemplateName, pParentWnd )
{
}
CMyDlg::CMyDlg(UINT nIDTemplate, CWnd* pParentWnd)
: CDialog(nIDTemplate, pParentWnd )
{
}
接着让某个和资源绑定的对话框类继承 COneDlg:public CMyDlg ,接着
CSecondDlg: public COneDlg,
只要构造函数写对了,一切OK!
若还有其他已经绑定资源的对话框,就让他们去继承COneDlg,之后添加消息映射应该就能实现了。

研究进行中,还差个DLL内绑带资源的问题没解决,请各位继续关注本贴!
cdef9108 2008-10-26
  • 打赏
  • 举报
回复
先,mark以下
cnzdgs 2008-10-26
  • 打赏
  • 举报
回复
你描述的有些混乱,COneDlg、CSendDlg、CSecondDlg、TwoDlg.h之间是什么关系?基类中不要使用其派生类。
Fireway2008 2008-10-26
  • 打赏
  • 举报
回复
经过一个晚上的研究,现在向各位再提一个关于继承和类包含的问题 :

按本人的计划,写一个类 COneDlg:public CMyDlg ,接着 CSecondDlg: public COneDlg,
其中COneDlg绑定了IDD_ONE_DLG CSecondDlg绑定了IDD_TWO_DLG

1.现在在COneDlg内有一个按钮,给这个按钮添加消息响应 ,打算单击后可以打开CSendDlg类的一个对象
void COneDlg::OnOpen()
{
CSendDlg*dlg;
dlg = new CSendDlg(IDD_TWO_DLG);
dlg->Create(IDD_TWO_DLG, NULL);
dlg->ShowWindow(SW_SHOW);
}
我在COneDlg.h内包含了头文件#include "TwoDlg.h"
2.CSecondDlg内,因为有CSecondDlg: public COneDlg,所以在CSecondDlg.h内#include "OneDlg.h"
结果一编译,错误连篇!



主要错误如下:
error C2504: 'COneDlg' : base class undefined OneDlg.cpp
error C2504: 'COneDlg' : base class undefined OneDlg.cpp
哪位高手可以指点一下正确的文件包含方式?
Fireway2008 2008-10-26
  • 打赏
  • 举报
回复
18楼的朋友,你说的也许有道理。
我的想法就是打算让代码可重用率达到最优,难道不是程序开发的思想之一?

现在我有2个新问题:在写继承的时候遇到的
1.让某个和资源绑定的对话框类继承 COneDlg:public CMyDlg ,接着
CSecondDlg: public COneDlg,如果ConeDlg里边有这样一个函数,void change()在CSendDlg里边,如果要使得同名函数拥有同样的功能,只要用COneDlg::Change();就可以了,不是很方便吗,省去再次书写重复罗嗦的代码 ?

2.另外,你说CDialog类的实现本身就有些问题,能否举个具体的例子?

谢谢!
CaptainIII 2008-10-26
  • 打赏
  • 举报
回复
ID就是个数字,MFC自己区别资源用的。你没有为你要解决的问题找到合适的解决方法,只能是事情越做越多,ms造个CDialog,就是对窗口的一种封装,你想做的东西,并非是它的规范用法。用SDK,自己建立窗口。或者改变软件的使用方法。这样折腾,除了对MFC一些奇怪的特性增加了了解外,没有多大提高。CDialog类的实现代码就在开发环境中,可以打开来自己看看。它实现的本身就有些问题,当然与你现在所用的还没有关系。
cnzdgs 2008-10-25
  • 打赏
  • 举报
回复
[Quote=引用 13 楼 Fireway2008 的回复:]
我主要是为了让其他几个子对话框实现和主对话框COneDlg一样的功能,所以他们均pulic COneDlg

可是,这样做了,发现头文件包含很混乱……,而且,声明的其中一个子对话框CSecondDlg
#include "OneDlg.h"//main dlg
class CSecondDlg : public COneDlg
{
// Construction
public:
CSecondDlg(CWnd* pParent = NULL); // standard constructor我感觉这行写的不规范,导致 error C2504: 'COneDlg' : base class und…
[/Quote]
这个错误是没有找到COneDlg的定义,可能是你循环包含头文件,导致OneDlg.h在编译时被跳过了。
cnzdgs 2008-10-25
  • 打赏
  • 举报
回复
[Quote=引用 12 楼 Fireway2008 的回复:]

我突然有个新想法,在对话框绑定处有一个 enum { IDD = IDD_ONE_DIALOGCOPY };
是否可以利用enum 枚举多个不同ID 的对话框?然后就按你说的那种方式,分情况载入对话框。

这个想法现实吗? enum { ????如何写为好呢 };

各位有何看法?
[/Quote]
这样做也可以,不过没多大意义。
cnzdgs 2008-10-25
  • 打赏
  • 举报
回复
[Quote=引用 10 楼 Fireway2008 的回复:]
提个小问题,当把一个类完整输出成为DLL,在编译,链接的时候,用 Debug 和Realse的方式似乎都可以生成合适的 lib和 dll文件供程序调用, 他们有什么差别呢? 我认为Realse出来的DLL自然有他的优势,各位意下如何?
[/Quote]
Debug编译出来的程序包含调试信息,在调试时使用,Release编译没有调试信息,并做了优化,在发布时使用。两种方式编译得到的lib都可以用。
Fireway2008 2008-10-25
  • 打赏
  • 举报
回复
我主要是为了让其他几个子对话框实现和主对话框COneDlg一样的功能,所以他们均pulic COneDlg

可是,这样做了,发现头文件包含很混乱……,而且,声明的其中一个子对话框CSecondDlg
#include "OneDlg.h"//main dlg
class CSecondDlg : public COneDlg
{
// Construction
public:
CSecondDlg(CWnd* pParent = NULL); // standard constructor
我感觉这行写的不规范,导致 error C2504: 'COneDlg' : base class undefined
}
在源文件里边,
CSecondDlg::CSecondDlg(CWnd* pParent /*=NULL*/)
: COneDlg(pParent)

{
//{{AFX_DATA_INIT(CSecondDlg)
// NOTE: the ClassWizard will add member initialization here
//}}AFX_DATA_INIT
}

请问各位应该怎么处理好呢?
Fireway2008 2008-10-25
  • 打赏
  • 举报
回复

我突然有个新想法,在对话框绑定处有一个 enum { IDD = IDD_ONE_DIALOGCOPY };
是否可以利用enum 枚举多个不同ID 的对话框?然后就按你说的那种方式,分情况载入对话框。

这个想法现实吗? enum { ????如何写为好呢 };


各位有何看法?
zhoujianhei 2008-10-25
  • 打赏
  • 举报
回复
一个主对话框,若干个子对话框,需要哪个就显示哪个。
Fireway2008 2008-10-25
  • 打赏
  • 举报
回复
提个小问题,当把一个类完整输出成为DLL,在编译,链接的时候,用 Debug 和Realse的方式似乎都可以生成合适的 lib和 dll文件供程序调用, 他们有什么差别呢? 我认为Realse出来的DLL自然有他的优势,各位意下如何?
Fireway2008 2008-10-25
  • 打赏
  • 举报
回复
不好意思,各位,我刚才晕了 ……
因为我改变了构造函数,所以只要

CTESTMYDLGDlg dlg; 改为 --->
CTESTMYDLGDlg dlg(IDD_TESTMYDLG_DIALOG); OK
Fireway2008 2008-10-25
  • 打赏
  • 举报
回复
我是这样写的,CMyDlg 类内,按一楼的方法进行了函数重载,在MyDlg.cpp内
CMyDlg::CMyDlg(LPCTSTR lpszTemplateName, CWnd* pParentWnd)
: CDialog(lpszTemplateName, pParentWnd )
{
}
CMyDlg::CMyDlg(UINT nIDTemplate, CWnd* pParentWnd)
: CDialog(nIDTemplate, pParentWnd )
{
}

CMyDlg::~CMyDlg()
{
}
并且在这个类里边测试性地加入了屏蔽回车导致对话框关闭的
BOOL CMyDlg::PreTranslateMessage(MSG* pMsg)
{
if ( pMsg->message == WM_KEYDOWN )
{
switch(pMsg->wParam)
{
case VK_RETURN://屏蔽作用
return TRUE;
break;
}
}
return CWnd::PreTranslateMessage(pMsg);
}

之后,用MFC创建了一个基于对话框的程序,工程名TESTMYDLG
之后手动修改其CTESTMYDLGDlg类内的构造函数,在TESTMYDLGDlg.h内声明如下
#include "MyDlg.h"
class CTESTMYDLGDlg : public CMyDlg//引入通用对话框类
//class CTESTMYDLGDlg : public CDialog
{
// Construction
public:
// CTESTMYDLGDlg(CWnd* pParent = NULL); // standard constructor
CTESTMYDLGDlg(LPCTSTR lpszTemplateName, CWnd* pParentWnd = NULL);
CTESTMYDLGDlg(UINT nIDTemplate, CWnd* pParentWnd = NULL);
// Dialog Data
//{{AFX_DATA(CTESTMYDLGDlg)
enum { IDD = IDD_TESTMYDLG_DIALOG };//被绑定的对话框ID
// NOTE: the ClassWizard will add data members here
//}}AFX_DATA

……
};

TESTMYDLGDlg.cpp内
CTESTMYDLGDlg::CTESTMYDLGDlg(LPCTSTR lpszTemplateName, CWnd* pParentWnd)
: CMyDlg(lpszTemplateName, pParentWnd )
{
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
CTESTMYDLGDlg::CTESTMYDLGDlg(UINT nIDTemplate, CWnd* pParentWnd)
: CMyDlg(nIDTemplate, pParentWnd )
{
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}

最后在对话框IDD_TESTMYDLG_DIALOG上添加了一些控件和他们的消息影射。

编译的时候在 BOOL CTESTMYDLGApp::InitInstance()内报错
出错行
CTESTMYDLGDlg dlg;//here
m_pMainWnd = &dlg;
int nResponse = dlg.DoModal();
error C2512: 'CTESTMYDLGDlg' : no appropriate default constructor available
不知如何解决……
还请各位高手指点!
  • 打赏
  • 举报
回复
初始化的时候MoveWindow就可以了
用同一个类,同一个资源
cnzdgs 2008-10-24
  • 打赏
  • 举报
回复
用MFC规则DLL有什么问题?相关代码是怎么写的?

用DLL的情况,我想到的主要有三种:
1、同一个模块可能被多个应用程序使用,其中包括全局Hook之类。
2、为了开放功能接口给其它应用程序调用。
3、对模块的独立性有要求较高,以便多人开发和定制软件功能。
加载更多回复(5)

15,471

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC 进程/线程/DLL
社区管理员
  • 进程/线程/DLL社区
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告
暂无公告

试试用AI创作助手写篇文章吧