小球遇屏幕边界反弹(VC++6.0——MFC)
题目:在视图中画个圆,设定好圆的初始运动速度,碰到边框后可以反弹。
步骤
1、打开VC6.0,点击屏幕左上角“文件(F)”,选择“新建(N)… Ctrl_N”。
2、在弹出的对话框中,选择“工程 >> MFC AppWizard(exe)”,选择创建工程的位置并给工程命名,点击“确定”。
3、选择“单文档(S)”,点击“完成”,点击“确定”,如下图所示。
4、画一个填充圆,如下图所示。
代码如下:
void CExercise1View::DrawCircle(CDC *pDC, CPoint Center, int radius)
{
CBrush brush, *pOldBrush; //旧画刷的指针
brush.CreateSolidBrush(RGB(255,0,0));
pOldBrush = pDC->SelectObject(&brush);
pDC->Ellipse(Center.x - radius,Center.y - radius,Center.x + radius,Center.y + radius);
brush.DeleteObject();
pDC->SelectObject(pOldBrush);
}
5、定义一个圆的结构体,如下图所示。
代码如下:
typedef struct
{
POINT center; //定义圆心
int radius; //定义半径
int vx,vy; //定义小球速度v大小和方向
}MyCircle; //定义圆对象
/****************************************************************************************************************/
在OnDraw()中调用圆:
DrawCircle(pDC,CPoint(m_circle.center.x,m_circle.center.y),m_circle.radius);
6、添加菜单并COMMAND,如下图所示。
7、碰撞检测条件判定,如下图所示。
代码如下:
void CExercise1View::CircleMoveAdjust(MyCircle &circle, RECT rect) //&为引用
{
if(circle.center.y + circle.radius >= rect.bottom)
{
circle.vy = -circle.vy;
} //碰底
if(circle.center.x + circle.radius >= rect.right)
{
circle.vx = -circle.vx;
} //碰右
if(circle.center.y - circle.radius <= rect.top)
{
circle.vy = -circle.vy;
} //碰顶
if(circle.center.x - circle.radius <= rect.left)
{
circle.vx = -circle.vx;
} //碰左
return;
}
8、初始化小球位置、半径大小及速度大小,如下图所示。
代码如下:
CExercise1View::CExercise1View()
{
// TODO: add construction code here
m_circle.center.x = 300; m_circle.center.y = 200;
m_circle.radius = 10;
m_circle.vx = m_circle.vy = 10; //球的水平和竖直两个方向的分速度,速度v=10*sqrt(2)
//当小球速度和半径相等的话,碰撞检测是非常准确的
}
9、在OnTimer()中实现定时控制,如下图所示。
代码如下:
void CExercise1View::OnTimer(UINT nIDEvent)
{
// TODO: Add your message handler code here and/or call default
GetClientRect(&m_rect); //获得屏幕显示区域大小结构体
CircleMoveAdjust(m_circle,m_rect);
m_circle.center.x += m_circle.vx;
m_circle.center.y -= m_circle.vy; //改变当前小球的位置
Invalidate(true);
CView::OnTimer(nIDEvent);
}
10、运行结果,如下图所示。
可随意拖动改变屏幕大小,都能使小球遇到屏幕边界时反弹。