首页
社区
课程
招聘
[求助]关于MFC函数Get****Rect的问题
发表于: 2009-4-14 18:57 8123

[求助]关于MFC函数Get****Rect的问题

2009-4-14 18:57
8123
MFC里CWnd类有这样两个函数:
void GetWindowRect(
   LPRECT lpRect 
) const;




void GetClientRect(
   LPRECT lpRect 
) const;


在下初学MFC,被这两个函数给搞得头昏脑胀,希望各位高人能帮助在下解答以下几处疑惑,不胜感激!

1、对函数GetWindowRect,MSDN里的解释是:
The dimensions are given in screen coordinates relative to the upper-left corner of the display screen. The dimensions of the caption, border, and scroll bars, if present, are included.


这个display screen指的是上一层窗口么?比方说,我在一个对话框里放了CEdit控件myeidt,
那么myedit.GetWindowRect(&rect);所得的rect是不是就是myedit相对于对话框左上角的位置?那么如果我调用对话框的的GetWindowRect函数,this->GetWindowRect(&rect),返回的rect是不是应该是相对于屏幕左上角的位置,但我曾用MessageBox输出过,发现如果调用对话框的GetWindowRect,那么返回的CRect的left和top都是0,这岂不是与MSDN的描述矛盾啊?

2、如果我想获取一个Group Box控件的位置大小矩形,目的是为了用CBrush画图形,使之正好在Group Box中间并匹配Group Box的大小,用如下代码:

typedef struct _MY_ELLIPSE {
	CRect rect;
	CBrush brush;
} MY_ELLIPSE;


MY_ELLIPSE MyEllipse;
CStatic GroupBox;//已与一个Group Box控件关联
BOOL CBrushDlgDlg::OnInitDialog()
{
	CDialog::OnInitDialog();

	CRect TempRect;
	this->GroupBox.GetWindowRect(&TempRect);
	MyEllipse.rect=CRect(TempRect.left,TempRect.top,TempRect.right,TempRect.bottom);

	this->MyEllipse[0].brush.CreateSolidBrush(RGB(0,0,255));

	return TRUE;  // 除非将焦点设置到控件,否则返回 TRUE
}

void CBrushDlgDlg::OnPaint()
{
	if (IsIconic())
	{
		……
	}
	else
	{
		CClientDC cdc(this);
		CBrush* pOldBrush=NULL;
		pOldBrush=cdc.SelectObject(&this->MyEllipse.brush);
		cdc.Ellipse(&this->MyEllipse.rect);
		cdc.SelectObject(pOldBrush);
		CDialog::OnPaint();
	}
}


但是编译运行后,图形画出来明显偏右下,并且大小也过大,这个GetWindowRect返回的矩形为什么与Group Box一点也不匹配呢?

3、各位都是怎么完成类似2中的目的的呢,简单概括地说,就是有两个个控件,希望第二个控件的位置能动态地由第一个控件决定。我也不知道“动态”这个词用得是否准确,就是不能在资源窗口组合好,而要在运行时放好。

希望能有高人解惑,再次拜谢!

[培训]内核驱动高级班,冲击BAT一流互联网大厂工作,每周日13:00-18:00直播授课

收藏
免费 0
支持
分享
最新回复 (6)
雪    币: 130
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
2
GetWindowRect 获取的是屏幕坐标
GetClientRect 获取的是在父窗口的相对坐标
2009-4-14 19:21
0
雪    币: 240
活跃值: (25)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
3
其实我开始也是这么想的,但经过试验以后,好像不是……
2009-4-14 22:09
0
雪    币: 183
活跃值: (36)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
4
我也试过,和书剑秀才的结论一样。到现在也没搞明白,之后只好索性不做那个矩形块了。
郁闷中,等高手
还试过DPTOLP,LPTODP还是不行
2009-4-14 23:16
0
雪    币: 130
活跃值: (10)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
5
抱歉说错一点,GetClientRect 返回的是窗口大下,left,top始终为零

你的代码主要存在的问题是 GetWindowRect 获取的是屏幕坐标,而CClientDC 是你的对话框dc,
坐标和画布完全不匹配..,需要ScreenToClient转换一下

CClientDC dc(this);
                CBrush brush;
                RECT rc;

                CWnd* st = GetDlgItem(IDC_STATIC1);

                brush.CreateSolidBrush(RGB(255, 0, 0));
                st->GetWindowRect(&rc);
                ScreenToClient(&rc);

                CBrush* oldBrush = dc.SelectObject(&brush);
                dc.Ellipse(&rc);
                dc.SelectObject(oldBrush);
2009-4-15 00:52
0
雪    币: 240
活跃值: (25)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
6
先谢谢sojoo的热心回答。

可能是我说的不够清楚:

我在这段代码中插了个MessageBox,结果发现GetWindowRect()返回的CRect的left和top也是0!!

BOOL CBrushDlgDlg::OnInitDialog()
{
  CDialog::OnInitDialog();

  CRect TempRect;
  this->GroupBox.GetWindowRect(&TempRect);
[COLOR="Red"]  CString winSize;
  winSize.Format(L"left=%d,right=%d,top=%d,bottom=%d",TempRect.left,TempRect.right,TempRect.top,TempRect.bottom);
  this->MessageBox(winSize);[/COLOR]
  MyEllipse.rect=CRect(TempRect.left,TempRect.top,TempRect.right,TempRect.bottom);

  this->MyEllipse[0].brush.CreateSolidBrush(RGB(0,0,255));

  return TRUE;  // 除非将焦点设置到控件,否则返回 TRUE
}



这个,与MSDN上的参考好像矛盾的……
2009-4-15 16:11
0
雪    币: 240
活跃值: (25)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
7
想明白了,是我糊涂了:

我的GetWindowRect()函数用在了CBrushDlgDlg::OnInitDialog()里,这个时候CBrushDlgDlg::OnPaint()还没有执行,所以根本就不知道对话框相对于屏幕的位置。
经过试验,把etWindowRect()用在CBrushDlgDlg::OnPaint()里就OK了。

再次感谢sojoo兄的热心帮助!!
2009-4-15 16:39
0
游客
登录 | 注册 方可回帖
返回
//