最近利用VS2005编写了个工具,需要可以调节界面大小,研究了好些天,终于解决。整理如下
主要是利用onsize,重写onsize实现的
注:
1)若界面无法调整大小,则是因为界面属性少了个调整大小的属性,需进到*.rc中,添加上
2)如果有下拉框,需将下拉框中的属性Type是否为Drop List,否则改变界面大小时,会出现如下界面情况:
主界面跟子界面的关系:
//CRO2TestDlg.h中定义
CTabCtrl m_tabCtrl;
//在BEGIN_MESSAGE_MAP(CRO2TestDlg, CDialog)中添加上:
ON_WM_SIZE()//调整界面大小
//在CRO2TestDlg.cpp的DoDataExchange函数中输入:
DDX_Control(pDX, IDC_TAB1, m_tabCtrl);
//CRO2TestDlg.cpp的OnInitDialog函数中添加如下:
m_tabCtrl.InsertItem(0,"出厂设置");
m_tabCtrl.InsertItem(1,"主参配置");
m_tabCtrl.InsertItem(2,"高级设置");
m_tabCtrl.InsertItem(3,"报警设置");
m_tabCtrl.InsertItem(4,"消息设置");
m_tabCtrl.InsertItem(5,"监控设置");
m_tabCtrl.InsertItem(6,"行车记录仪");
//设置IDC_TAB1为父窗口
//m_para1 ~m_para7为7个新增界面,IDD_DIALOG1~IDD_DIALOG7为其对应的ID号
m_para1.Create(IDD_DIALOG1,GetDlgItem(IDC_TAB1));
m_para2.Create(IDD_DIALOG2,GetDlgItem(IDC_TAB1));
m_para3.Create(IDD_DIALOG3,GetDlgItem(IDC_TAB1));
m_para4.Create(IDD_DIALOG4,GetDlgItem(IDC_TAB1));
m_para5.Create(IDD_DIALOG5,GetDlgItem(IDC_TAB1));
m_para7.Create(IDD_DIALOG7,GetDlgItem(IDC_TAB1));
m_para6.Create(IDD_DIALOG6,GetDlgItem(IDC_TAB1));
//调整界面大小
CRect rect;
GetWindowRect(&rect);
oSize.x = rect.right - rect.left;
oSize.y = rect.bottom - rect.top;
//获得IDC_TAB1客户区大小
CRect rc;
m_tabCtrl.GetClientRect(&rc);
//调整子对话框在父窗口中的位置
rc.top += 20;
//rc.bottom -= 8;
rc.bottom += 4;
rc.left += 4;
rc.right -= 4;
//设置子对话框尺寸并移动到指定位置
m_para1.MoveWindow(&rc);
m_para2.MoveWindow(&rc);
m_para3.MoveWindow(&rc);
m_para4.MoveWindow(&rc);
m_para5.MoveWindow(&rc);
m_para7.MoveWindow(&rc);
m_para6.MoveWindow(&rc);
//分别设置隐藏和显示
m_para1.ShowWindow(true);
m_para2.ShowWindow(false);
m_para3.ShowWindow(false);
m_para4.ShowWindow(false);
m_para5.ShowWindow(false);
m_para7.ShowWindow(false);
m_para6.ShowWindow(false);
//-------------------------------------------------
/*重写Onsize*/
//对话框尺寸变化时,对话框内的控件随之改变大小函数
//--------------------------------------------------
void CRO2TestDlg::OnSize(UINT nType, int cx, int cy)
{
CDialog::OnSize(nType, cx, cy);
CWnd hWnd;
if (nType==SIZE_RESTORED || nType==SIZE_MAXIMIZED)
{
float ratio[2];
POINT newDialogSize;
CRect newRect;
//获取新的客户区的大小
GetWindowRect(&newRect);
newDialogSize.x = newRect.right - newRect.left;
newDialogSize.y = newRect.bottom - newRect.top;
//得现在的对话框与以往对话框的大小比例
ratio[0] = (float)newDialogSize.x / oSize.x;
ratio[1] = (float)newDialogSize.y / oSize.y;
CRect Rect;
int woc;
//左右上角的数据
CPoint OldTLPoint, NewTLPint;
CPoint OldBRPoint, NewBRPint;
//列出所有控件
HWND hwndChild = ::GetWindow(m_hWnd,GW_CHILD);//获取窗体子控件指针
while(hwndChild)
{
//取得ID
woc = ::GetDlgCtrlID(hwndChild);
GetDlgItem(woc)->GetWindowRect(Rect);
ScreenToClient(Rect);//将控件大小转换为在对话框中的区域坐标
OldTLPoint = Rect.TopLeft();//左上角
NewTLPint.x = long(OldTLPoint.x*ratio[0]);
NewTLPint.y = long(OldTLPoint.y*ratio[1]);
OldBRPoint = Rect.BottomRight();//右下角
NewBRPint.x = long(OldBRPoint.x*ratio[0]);
NewBRPint.y = long(OldBRPoint.y*ratio[1]);
Rect.SetRect(NewTLPint,NewBRPint);
if(woc == IDC_STATIC12 || woc == IDC_CHECK1 || woc == IDC_DEV_CHECK || woc == IDC_HIG_CHECK || woc == IDC_ALA_CHECK ||
woc == IDC_NEW_CHECK || woc == IDC_WAT_CHECK || woc == IDC_XCJL_CHECK)//只改变其顶点位置
GetDlgItem(woc)->MoveWindow(OldTLPoint.x,Rect.top,(OldBRPoint.x - OldTLPoint.x),(OldBRPoint.y - OldTLPoint.y),TRUE);
else
GetDlgItem(woc)->MoveWindow(Rect,TRUE);
hwndChild=::GetWindow(hwndChild, GW_HWNDNEXT);//获取该窗口下的子控件指针
}
//修改tab control中的子界面
CRect rectPara1;
m_tabCtrl.GetClientRect(&rectPara1);
//调整子对话框在父窗口中的位置
rectPara1.top += 20;
rectPara1.bottom += 4;
rectPara1.left += 4;
rectPara1.right -= 4;
m_para1.MoveWindow(&rectPara1);
m_para2.MoveWindow(&rectPara1);
m_para3.MoveWindow(&rectPara1);
m_para4.MoveWindow(&rectPara1);
m_para5.MoveWindow(&rectPara1);
m_para6.MoveWindow(&rectPara1);
m_para7.MoveWindow(&rectPara1);
//获取视频窗口父窗口的大小
::GetClientRect(hWnd, Rect);
oSize = newDialogSize;
}
}
以上代码,就可以实现主界面上的控件,以及子界面(不包括子界面上的控件)随着主界面的大小,而比例变化
若要实现子界面上的控件随之变化,需添加以下代码:
(这边只讲一个子界面《其他子界面类似》)
在子界面的.h中添加上
public:
POINT oParaSize1;//窗口2的界面大小
afx_msg void OnSize(UINT nType, int cx, int cy);//调整界面大小
然后在其.cpp中的BEGIN_MESSAGE_MAP(CPara1, CDialog)中,添加上
ON_WM_SIZE()//调整界面大小 无法使用
重写onsize
//调整界面大小
/*重写Onsize
*/
//-------------------------------------------------
//对话框尺寸变化时,对话框内的控件随之改变大小函数
//--------------------------------------------------
void CPara1::OnSize(UINT nType, int cx, int cy)
{
CDialog::OnSize(nType, cx, cy);
CWnd hWnd;
//CRO2TestDlg dlg;
if (nType==SIZE_RESTORED || nType==SIZE_MAXIMIZED)
{
float ratio[2];
POINT newDialogSize;
CRect newRect;
//获取新的客户区的大小
GetWindowRect(&newRect);
newDialogSize.x = newRect.right - newRect.left;
newDialogSize.y = newRect.bottom - newRect.top;
//得现在的对话框与以往对话框的大小比例
ratio[0] = (float)newDialogSize.x / oParaSize1.x;
ratio[1] = (float)newDialogSize.y / oParaSize1.y;
CRect Rect;
int woc;
//左右上角的数据
CPoint OldTLPoint, NewTLPint;
CPoint OldBRPoint, NewBRPint;
//列出所有控件
HWND hwndChild = ::GetWindow(m_hWnd,GW_CHILD);//获取窗体子控件指针
while(hwndChild)
{
//取得ID
woc = ::GetDlgCtrlID(hwndChild);
GetDlgItem(woc)->GetWindowRect(Rect);
ScreenToClient(Rect);//将控件大小转换为在对话框中的区域坐标
OldTLPoint = Rect.TopLeft();//左上角
NewTLPint.x = long(OldTLPoint.x*ratio[0]);
NewTLPint.y = long(OldTLPoint.y*ratio[1]);
OldBRPoint = Rect.BottomRight();//右小角
NewBRPint.x = long(OldBRPoint.x*ratio[0]);
NewBRPint.y = long(OldBRPoint.y*ratio[1]);
Rect.SetRect(NewTLPint,NewBRPint);
//如果是下拉框
if(woc == IDC_GPS_TYPE || woc == IDC_ZJ_FLAG || woc == IDC_SDDB_SWI || woc == IDC_DEADZONE_TYPE || woc == IDC_DEADZONE_ONETYPE || woc == IDC_DEADZONE_TWOTYPE)
GetDlgItem(woc)->MoveWindow(Rect.left,Rect.top,Rect.Width(),Rect.Height() + 200,TRUE);//+200表示下拉长度
else
GetDlgItem(woc)->MoveWindow(Rect,TRUE);
hwndChild=::GetWindow(hwndChild, GW_HWNDNEXT);//获取该窗口下的子控件指针
}
//获取视频窗口父窗口的大小
::GetClientRect(hWnd, Rect);
oParaSize1 = newDialogSize;
}
}
效果图:
原图:
变大后的:
变小后的:
可能调的不是很好,我也是最近自己百度,然后琢磨出来的!
如果你有更好的方法,求不吝赐教