对象与资源

对象与资源
还是以进度栏为例
在自定义消息中,进度栏创建完成后,还存在一些问题。
问题1:
创建完成后,当移动窗口,进度栏只能存在于固定的位置,并不能随碰着窗口大小改变而改变。
原因:
当窗口的尺寸区域发生变化的时候,那么状态栏的尺寸区域也要发生变化,
那么,最早所获取的窗格也就不准确了,所以就看到进度栏脱离了状态栏上的方格。
解决:
避免这种情况就需要在窗口发生变化时,重新去获取固定索引的区域,然后将进度栏移动到这个
区域冯冯当中。
发送WM_PAINT的消息,在这里面重新获取窗格的矩形区域,然后将其重新移动至距形区域
在CMianFrame中添加WM_PAINT消息。并添加处理函数。如下:
void CMainFrame::OnPaint()
{
	CPaintDC dc(this); // device context for painting
	
	CRect rect;
	m_wndStatusBar.GetItemRect(5,&rect);//得到所在的距形区域的大小

	
	m_progess.Create(WS_CHILD|WS_VISIBLE|PBS_SMOOTH, rect , 
		&m_wndStatusBar,111);

	m_progess.SetPos(50);
		// TODO: 在此处添加消息处理程序代码
		// 不为绘图消息调用 CFrameWnd::OnPaint()
}

那么是不是这做就OK 了?运行之后,会发生如下错误:
图一

这是为什么?通过调试,设置断点。

在进行初始化的时候,先运行至上面。然后

又到Onpaint函数中,rect 值的变化和对象m_progres变化如下图:

然后又运行至Onprogress()函数当中,以再次调用到对象m_progress 也同时创建使用相同的资源



然后进而出如上的错误。

经过跟踪发现,生成的过程,用相同的对象即为m_progress用到了两次,并且同一对象,用到创建相同的资源,所以
会出错。
就是说必须把对象相关的资源销毁,才能重新调用 

解决方案:可以把PostMessage()注释掉,即然用到Onpaint()进行重绘,就不需要自定义消息了。



但这样已经行了吗?当生成窗口后我们拉动窗口,其大小发生变化,还是会发生如图一的错误!

其实还是一样的错误 ,当窗口发生改变时候,就会发送一个wm_paint的消息,于是就会调用Onpaint()这个消息
响应函数,因为我们已经创建进度栏,并且已经将它与CProgressCtrl对象相关联,又一次去创建,当然会发生问题。
可以在Onpaint函数 中进行判断:对象m_progress是否关联了相关的资源?
void CMainFrame::OnPaint()
{
	CPaintDC dc(this); // device context for painting
	
	CRect rect;
	m_wndStatusBar.GetItemRect(5,&rect);//得到所在的距形区域的大小

	if(!m_progess.m_hWnd)
	{
	m_progess.Create(WS_CHILD|WS_VISIBLE|PBS_SMOOTH, rect , 
		&m_wndStatusBar,111);
	}
	else
		m_progess.MoveWindow(rect);
	m_progess.SetPos(50);
		// TODO: 在此处添加消息处理程序代码
		// 不为绘图消息调用 CFrameWnd::OnPaint()
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值