急,关于一个对话框类对应多套资源的问题?

scq2099yt 2008-10-09 11:45:31
开发平台:VC6.0+Windows Server 2003
程序模式:MFC对话框应用程序

对话框应用程序无标题栏,初始化时全屏显示。
对话框以bmp位图作为背景,对话框上放置了很多控件,这些控件也以bmp位图为背景,各控件的位置和背景图片中的图形有相对位置关系。
对话框背景图片尺寸为1024*768。

出现的问题如下:
如果在显示器分辨率为1024*768的情况下,没有问题,但是如果在显示器分辨率为其它的情况时,则控件位置和背景图片中的图形相对位置会错乱?
问题一:有没有比较好的或者是常用的处理这种问题的方法?

想到的解决方案如下:
方案一:定义多套对话框类和资源,分别对应不同分辨率调整好相对位置,然后在应用程序的InitInstance()函数中判断屏幕分辨率,根据分辨率决定启动哪个对话框。这个方案可行(推测而已,没试过),但是很费时间,方法比较笨。

方案二:只有一个对话框类,但是有多套对话框资源,这些对话框资源上的内容一样,只是控件位置的相对位置不一样,适应于各种分辨率。
问题二:如何在对话框启动时,动态为其加载对话框资源?

在对话框类的头文件中,有如下自动生成的代码:
// Dialog Data
//{{AFX_DATA(CXXXDlg)
enum { IDD = IDD_XXX_DIALOG };
//}}AFX_DATA
问题三:在enum 中用不同的资源ID,则启动时就会加载该对话框资源作为对话框类的资源,但是如何动态选择对话框资源ID呢?

问题三:是否可以在这段自动生存的代码中添加判断语句,通过判断分辨率来决定动态加载的对话框资源ID?

如果将上面自动生成的代码改成如下:
// Dialog Data
//{{AFX_DATA(CXXXDlg)
enum { IDD = IDD_XXX_DIALOG, IDD = IDD_XXX_DIALOG1, IDD = IDD_XXX_DIALOG2, ... };
//}}AFX_DATA
问题四:如果这样的话,应用程序中如何控制这个enum的值来决定动态加载哪个对话框资源ID呢?

...全文
382 33 打赏 收藏 转发到动态 举报
写回复
用AI写文章
33 条回复
切换为时间正序
请发表友善的回复…
发表回复
Formular1 2008-10-09
  • 打赏
  • 举报
回复
动态加载资源
cnzdgs 2008-10-09
  • 打赏
  • 举报
回复
[Quote=引用 11 楼 scq2099yt 的回复:]
一种是对话框初始化时根据屏幕分辨率动态调整各个控件的位置和尺寸;
这种方式,控件与背景位图的图形之间的相对位置不太好的确定,不同的分辨率会有不同的相对位置。不知道我的理解是否正确?

另一种是向游戏一样,改变显示模式,将分辨率设置为1024*768,窗口关闭或者失去活动状态时恢复原显示模式。
这种方式,我已经试过了,也能达到效果,但是比较“流氓”,用户看了感觉不是很好。
[/Quote]
如果要支持的最高和最低分辨率相差越大,界面布局就越不好设计。

修改显示模式是很“流氓”,我只是提一下这种做法,并不推荐。其实程序上来就最大化也一样“流氓”。
scq2099yt 2008-10-09
  • 打赏
  • 举报
回复
to smallfishff 兄:
bmp自己绘制的话会增加编程的工作量,美工作就什么都省了。

cdialog dlg;

dlg.create(IDD_1)
else
dlg.create(IDD_2)

您说在应用程序类的函数InitInstance()中将下面代码改为上面的形式:
CTestDlg dlg;
m_pMainWnd = &dlg;
int nResponse = dlg.DoModal();
smallfishff 2008-10-09
  • 打赏
  • 举报
回复
你指的是bmp错乱吧.bmp是否可以手动绘制?那么相对位置的计算就不会有问题了.

资源替换的确是一种笨方法 使用AfxSetResourceHandle()变更可以完成.
动态替换已经有答案了 似乎这样也是可以.
cdialog dlg;

dlg.create(IDD_1)
else
dlg.create(IDD_2)
scq2099yt 2008-10-09
  • 打赏
  • 举报
回复
感谢 “签到” 兄,呵呵
scq2099yt 2008-10-09
  • 打赏
  • 举报
回复
to cnzdgs 大哥:
感谢您的回复。


一种是对话框初始化时根据屏幕分辨率动态调整各个控件的位置和尺寸;
这种方式,控件与背景位图的图形之间的相对位置不太好的确定,不同的分辨率会有不同的相对位置。不知道我的理解是否正确?


另一种是向游戏一样,改变显示模式,将分辨率设置为1024*768,窗口关闭或者失去活动状态时恢复原显示模式。
这种方式,我已经试过了,也能达到效果,但是比较“流氓”,用户看了感觉不是很好。
不过游戏中用这种方式我真没注意过,呵呵,学习了。
晚上回去试试魔兽是不是这样的,呵呵。

后面的其它问题都一样,改一下对话框类的构造函数,把资源ID作为参数传过来,使用该参数调用CDialog的构造函数。
这种方式,我试完回来报告结果。
dayong576 2008-10-09
  • 打赏
  • 举报
回复
签到
cnzdgs 2008-10-09
  • 打赏
  • 举报
回复
类中可以这样声明:
CTestDlg(LPCTSTR lpszTemplateName = CTestDlg::IDD, CWnd* pParent = NULL);
cnzdgs 2008-10-09
  • 打赏
  • 举报
回复
CTestDlg::CTestDlg(LPCTSTR lpszTemplateName, CWnd* pParent)
: CDialog(lpszTemplateName, pParent)
cnzdgs 2008-10-09
  • 打赏
  • 举报
回复
问题一:你的两种方案都可以,再提另外两种方案供你参考,一种是对话框初始化时根据屏幕分辨率动态调整各个控件的位置和尺寸;另一种是向游戏一样,改变显示模式,将分辨率设置为1024*768,窗口关闭或者失去活动状态时恢复原显示模式。

后面的其它问题都一样,改一下对话框类的构造函数,把资源ID作为参数传过来,使用该参数调用CDialog的构造函数。
scq2099yt 2008-10-09
  • 打赏
  • 举报
回复
to vcPlayer 兄

CTestDlg默认资源ID是IDD_TEST_DIALOG,新建的对话框资源ID为IDD_DIALOG1。
其默认构造函数为:
CTestDlg::CTestDlg(CWnd* pParent /*=NULL*/)
: CDialog(CTestDlg::IDD, pParent)
{
...
}

将其改为如下:
CTestDlg::CTestDlg(CWnd* pParent /*=NULL*/)
: CDialog(IDD_DIALOG1, pParent)
{
...
}

编译运行程序,程序自动加载了对话框资源IDD_DIALOG1,但是如何控制构造函数呢?
如何动态决定对话框资源ID呢?


scq2099yt 2008-10-09
  • 打赏
  • 举报
回复
感谢 vcPlayer 兄顶贴。

1、一般为拉伸,各子控件的背景在运行时确定(取大背景相应位置);
拉伸容易导致背景位图变形或者脱色。

2、能否在构造函数中实现?
CYourDlg::CYourDlg(dlgResourceID) : IDD(dlgResourceID)
{
};
这是个好建议,试完后回来报告结果,呵呵。


scq2099yt 2008-10-09
  • 打赏
  • 举报
回复
to jason_wentzel大哥:
控件自适应大小能够解决控件自身位置的问题,无法解决控件与背景位图上图形的相对位置问题。
vcPlayer 2008-10-09
  • 打赏
  • 举报
回复
顶一下:)!

1、一般为拉伸,各子控件的背景在运行时确定(取大背景相应位置);
2、能否在构造函数中实现?
CYourDlg::CYourDlg(dlgResourceID) : IDD(dlgResourceID)
{
};
3、4、5同2;

另外还要考虑一个问题:DPI,这个很难解决。
孤客天涯 2008-10-09
  • 打赏
  • 举报
回复
为什么不采用控件自适应大小的方式来解决?
scq2099yt 2008-10-09
  • 打赏
  • 举报
回复
sf
scq2099yt 2008-10-09
  • 打赏
  • 举报
回复

再次感谢 cnzdgs 和 vcPlayer 二位大哥。

二位的方法都可行,谢谢了先,揭帖了。

scq2099yt 2008-10-09
  • 打赏
  • 举报
回复
to SummerHeart 兄:

难道楼主的DLG背景是整张BMP吗?
是否有考虑过象有的网页BMP切片方法?

是一整张图片。
什么事情都有两面性。
图片过多也会导致位置改变的问题。

感谢boythl 兄。
11000000 2008-10-09
  • 打赏
  • 举报
回复
我认为方法一就可以,只要能实现就好,不然领导会骂的。
jarraytan 2008-10-09
  • 打赏
  • 举报
回复
游戏中一般是把分辨率往小改。 往大调的话,若显示器不支持呢?

最大化没什么关系吧? 比如IE,是能记住你上次关闭时窗体的大小和位置的。你上次最大化关了,下次开不也是最大化大小的。

[Quote=引用 26 楼 scq2099yt 的回复:]
to boythl 兄:

我的理解,您的方法跟方案一类似。
[/Quote]
恩。跟方案一差不多。 若是用delphi的话就一点都不笨。 因为它支持可视化编辑窗口,改ba改ba就好了。 唉, vc。
加载更多回复(13)

16,472

社区成员

发帖
与我相关
我的任务
社区描述
VC/MFC相关问题讨论
社区管理员
  • 基础类社区
  • Web++
  • encoderlee
加入社区
  • 近7日
  • 近30日
  • 至今
社区公告

        VC/MFC社区版块或许是CSDN最“古老”的版块了,记忆之中,与CSDN的年龄几乎差不多。随着时间的推移,MFC技术渐渐的偏离了开发主流,若干年之后的今天,当我们面对着微软的这个经典之笔,内心充满着敬意,那些曾经的记忆,可以说代表着二十年前曾经的辉煌……
        向经典致敬,或许是老一代程序员内心里面难以释怀的感受。互联网大行其道的今天,我们期待着MFC技术能够恢复其曾经的辉煌,或许这个期待会永远成为一种“梦想”,或许一切皆有可能……
        我们希望这个版块可以很好的适配Web时代,期待更好的互联网技术能够使得MFC技术框架得以重现活力,……

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