BOUNCE.C
资源名称:MSDN_VC98.zip [点击查看]
上传用户:bangxh
上传日期:2007-01-31
资源大小:42235k
文件大小:15k
源码类别:
Windows编程
开发平台:
Visual C++
- /******************************************************************************
- * This is a part of the Microsoft Source Code Samples.
- * Copyright (C) 1993-1997 Microsoft Corporation.
- * All rights reserved.
- * This source code is only intended as a supplement to
- * Microsoft Development Tools and/or WinHelp documentation.
- * See these sources for detailed information regarding the
- * Microsoft samples programs.
- ******************************************************************************/
- /*---------------------------------------------------------------------------*
- | BOUNCING BALL MODULE
- *---------------------------------------------------------------------------*/
- #include <windows.h>
- #include "gdidemo.h"
- #include "bounce.h"
- VOID XFormClear(PMYXFORM);
- VOID XFormScale(PMYXFORM,int,int);
- VOID XFormTrans(PMYXFORM,int,int);
- VOID XFormPoint(PMYXFORM,LPPOINT);
- /*---------------------------------------------------------------------------*
- | CREATE BOUNCE WINDOW PROCEDURE
- |
- *---------------------------------------------------------------------------*/
- HWND FAR CreateBounceWindow(HWND hWndClient, int nItem)
- {
- HANDLE hInstance;
- MDICREATESTRUCT mcs;
- static char buffer[256];
- hInstance = GETINSTANCE(hWndClient);
- LoadString (hInstance, BOUNCETITLE, buffer, 256);
- /*
- ** Initialize the MDI create struct for creation of the
- ** test window.
- */
- mcs.szClass = BOUNCECLASS;
- mcs.szTitle = buffer;
- mcs.hOwner = hInstance;
- mcs.x = CW_USEDEFAULT;
- mcs.y = CW_USEDEFAULT;
- mcs.cx = CW_USEDEFAULT;
- mcs.cy = CW_USEDEFAULT;
- mcs.style = 0l;
- mcs.lParam = (LONG)nItem;
- return((HWND)SendMessage(hWndClient,WM_MDICREATE,0,(LONG)(LPMDICREATESTRUCT)&mcs));
- }
- /*---------------------------------------------------------------------------*
- | BOUNCE WINDOW PROCEDURE
- |
- *---------------------------------------------------------------------------*/
- LONG APIENTRY BounceProc(HWND hWnd, UINT wMsg, WPARAM wParam, LONG lParam)
- {
- switch(wMsg)
- {
- case WM_CREATE:
- BounceCreateProc(hWnd);
- break;
- case WM_MOVE:
- BounceRefresh(hWnd);
- break;
- case WM_COMMAND:
- BounceCommandProc(hWnd,wParam,lParam);
- break;
- case WM_TIMER:
- BounceObjects(hWnd);
- break;
- case WM_PAINT:
- BouncePaintProc(hWnd);
- break;
- case WM_DESTROY:
- BounceDestroyProc(hWnd);
- break;
- default:
- return(DefMDIChildProc(hWnd,wMsg,wParam,lParam));
- }
- return(0l);
- }
- /*---------------------------------------------------------------------------*
- | BOUNCE CREATE PROCEDURE
- |
- *---------------------------------------------------------------------------*/
- BOOL BounceCreateProc(HWND hWnd)
- {
- PBOUNCEDATA pbd;
- if(AllocWindowInfo(hWnd,sizeof(BOUNCEDATA)))
- {
- if(pbd = (PBOUNCEDATA)LockWindowInfo(hWnd))
- {
- pbd->hBall1 = ballCreate(hWnd,20,20,RGB(255,0,0));
- pbd->hBall2 = ballCreate(hWnd,20,20,RGB(0,0,255));
- pbd->hBall3 = ballCreate(hWnd,20,20,RGB(0,255,0));
- pbd->hBall4 = ballCreate(hWnd,20,20,RGB(255,0,255));
- UnlockWindowInfo(hWnd);
- SetTimer(hWnd,1,50,NULL);
- return(TRUE);
- }
- FreeWindowInfo(hWnd);
- }
- return(FALSE);
- }
- /*---------------------------------------------------------------------------*
- | BOUNCE COMMAND PROCEDURE
- |
- *---------------------------------------------------------------------------*/
- BOOL BounceCommandProc(HWND hWnd, WPARAM wParam, LONG lParam)
- {
- hWnd = hWnd;
- wParam = wParam;
- lParam = lParam;
- return(TRUE);
- }
- /*---------------------------------------------------------------------------*
- | BOUNCE PAINT PROCEDURE
- |
- *---------------------------------------------------------------------------*/
- VOID BouncePaintProc(HWND hWnd)
- {
- HDC hDC;
- PAINTSTRUCT ps;
- if(hDC = BeginPaint(hWnd,&ps))
- EndPaint(hWnd,&ps);
- BounceRefresh(hWnd);
- return;
- }
- /*---------------------------------------------------------------------------*
- | BOUNCE DESTROY PROCEDURE
- |
- *---------------------------------------------------------------------------*/
- VOID BounceDestroyProc(HWND hWnd)
- {
- PBOUNCEDATA pbd;
- KillTimer(hWnd,1);
- if(pbd = (PBOUNCEDATA)LockWindowInfo(hWnd))
- {
- ballDestroy(pbd->hBall1);
- ballDestroy(pbd->hBall2);
- ballDestroy(pbd->hBall3);
- ballDestroy(pbd->hBall4);
- UnlockWindowInfo(hWnd);
- }
- FreeWindowInfo(hWnd);
- return;
- }
- /*---------------------------------------------------------------------------*
- | BOUNCE REFRESH
- |
- *---------------------------------------------------------------------------*/
- VOID BounceRefresh(HWND hWnd)
- {
- PBOUNCEDATA pbd;
- RECT rect;
- HDC hDC;
- POINT pDimensions;
- int xDirection,yDirection;
- if(pbd = (PBOUNCEDATA)LockWindowInfo(hWnd))
- {
- if(hDC = GetDC(hWnd))
- {
- GetClientRect(hWnd,&rect);
- FillRect(hDC,&rect,GETCLASSBRUSH(hWnd));
- xDirection = ((lRandom() % 5)+5);
- yDirection = ((lRandom() % 5)+5);
- ballSetPosition(pbd->hBall1,0,0);
- ballSetDirection(pbd->hBall1,xDirection,yDirection);
- ballGetDimensions(pbd->hBall2,&pDimensions);
- ballSetPosition(pbd->hBall2,rect.right-pDimensions.x,0);
- xDirection = -(((int)lRandom() % 5)+5);
- yDirection = ((lRandom() % 5)+5);
- ballSetDirection(pbd->hBall2,xDirection,yDirection);
- ballGetDimensions(pbd->hBall3,&pDimensions);
- ballSetPosition(pbd->hBall3,0,rect.bottom-pDimensions.y);
- xDirection = ((lRandom() % 5)+5);
- yDirection = -((int)(lRandom() % 5)+5);
- ballSetDirection(pbd->hBall3,xDirection,yDirection);
- ballGetDimensions(pbd->hBall4,&pDimensions);
- ballSetPosition(pbd->hBall4,rect.right-pDimensions.x,rect.bottom-pDimensions.y);
- xDirection = -((int)(lRandom() % 5)+5);
- yDirection = -((int)(lRandom() % 5)+5);
- ballSetDirection(pbd->hBall4,xDirection,yDirection);
- ballBounce(pbd->hBall1);
- ballBounce(pbd->hBall2);
- ballBounce(pbd->hBall3);
- ballBounce(pbd->hBall4);
- ReleaseDC(hWnd,hDC);
- }
- UnlockWindowInfo(hWnd);
- }
- return;
- }
- VOID BounceObjects(HWND hWnd)
- {
- PBOUNCEDATA pbd;
- if(pbd = (PBOUNCEDATA)LockWindowInfo(hWnd))
- {
- /*
- ** Determine if the balls hit any of the edges of the display. If
- ** they do, then these functions reset their position to something
- ** more desireable and re-do their direction.
- */
- CheckEdgePosition(hWnd,pbd->hBall1);
- CheckEdgePosition(hWnd,pbd->hBall2);
- CheckEdgePosition(hWnd,pbd->hBall3);
- CheckEdgePosition(hWnd,pbd->hBall4);
- ballBounce(pbd->hBall1);
- ballBounce(pbd->hBall2);
- ballBounce(pbd->hBall3);
- ballBounce(pbd->hBall4);
- UnlockWindowInfo(hWnd);
- }
- return;
- }
- VOID CheckEdgePosition(HWND hWnd, HANDLE hBall)
- {
- POINT pPos,pDir,pDim;
- int xNewPos,yNewPos,xNewDir,yNewDir;
- RECT rect;
- ballGetPosition(hBall,&pPos);
- ballGetDirection(hBall,&pDir);
- ballGetDimensions(hBall,&pDim);
- GetClientRect(hWnd,&rect);
- /*
- ** Check each edge of the client rectagle. If the ball goes past the
- ** boundries, reset the position and give it a new direction.
- */
- xNewDir = pDir.x;
- yNewDir = pDir.y;
- xNewPos = pPos.x+pDir.x;
- yNewPos = pPos.y+pDir.y;
- if(xNewPos < rect.left)
- {
- xNewDir = ((lRandom() % 5)+5);
- ballSetPosition(hBall,rect.left,pPos.y);
- }
- if((xNewPos+pDim.x) > rect.right)
- {
- xNewDir = -(((int)lRandom() % 5)+5);
- ballSetPosition(hBall,rect.right-pDim.x,pPos.y);
- }
- if(yNewPos < rect.top)
- {
- yNewDir = ((lRandom() % 5)+5);
- ballSetPosition(hBall,pPos.x,rect.top);
- }
- if((yNewPos+pDim.y) > rect.bottom)
- {
- yNewDir = -(((int)lRandom() % 5)+5);
- ballSetPosition(hBall,pPos.x,rect.bottom-pDim.y);
- }
- ballSetDirection(hBall,xNewDir,yNewDir);
- return;
- }
- /*---------------------------------------------------------------------------*
- | CLEAR XFORM
- |
- *---------------------------------------------------------------------------*/
- VOID XFormClear(PMYXFORM pXForm)
- {
- int Row,Col;
- for(Row=0; Row < 3; Row++)
- for(Col=0; Col < 3; Col++)
- if(Row == Col)
- pXForm->xForm[Row][Col] = 1;
- else
- pXForm->xForm[Row][Col] = 0;
- return;
- }
- /*---------------------------------------------------------------------------*
- | XFORM SCALE
- |
- *---------------------------------------------------------------------------*/
- VOID XFormScale(PMYXFORM pXForm, int xScale, int yScale)
- {
- int idx;
- for(idx=0; idx < 3; idx++)
- {
- pXForm->xForm[idx][0] = pXForm->xForm[idx][0] * xScale;
- pXForm->xForm[idx][1] = pXForm->xForm[idx][1] * yScale;
- }
- return;
- }
- VOID XFormTrans(PMYXFORM pXForm, int xTrans, int yTrans)
- {
- pXForm->xForm[2][0] = pXForm->xForm[2][0] + xTrans;
- pXForm->xForm[2][1] = pXForm->xForm[2][1] + yTrans;
- return;
- }
- VOID XFormPoint(PMYXFORM pXForm, LPPOINT pPoint)
- {
- int x,y;
- x = (pXForm->xForm[0][0] * pPoint->x) + (pXForm->xForm[1][0] * pPoint->y) + pXForm->xForm[2][0];
- y = (pXForm->xForm[0][1] * pPoint->x) + (pXForm->xForm[1][1] * pPoint->y) + pXForm->xForm[2][1];
- pPoint->x = x;
- pPoint->y = y;
- return;
- }
- /*
- ** -------------------------------
- ** -------------------------------
- ** -------------------------------
- */
- HANDLE ballCreate(HWND hWnd, int nWidth, int nHeight, COLORREF crColor)
- {
- HANDLE hBall;
- PBALLDATA pbd;
- if(hBall = LocalAlloc(LHND,sizeof(BALLDATA)))
- {
- if(pbd = (PBALLDATA)LocalLock(hBall))
- {
- pbd->hWnd = hWnd;
- pbd->nWidth = nWidth;
- pbd->nHeight = nHeight;
- pbd->xDirection = 0;
- pbd->yDirection = 0;
- pbd->bNewPosition = FALSE;
- pbd->xPosition = 0;
- pbd->yPosition = 0;
- pbd->crColor = crColor;
- XFormClear(&pbd->xForm);
- LocalUnlock(hBall);
- return(hBall);
- }
- LocalFree(hBall);
- }
- return(NULL);
- }
- BOOL ballDestroy(HANDLE hBall)
- {
- if(LocalFree(hBall))
- return(FALSE);
- return(TRUE);
- }
- VOID ballBounce(HANDLE hBall)
- {
- PBALLDATA pbd;
- HDC hDC;
- HBRUSH hBrush;
- POINT pOrg,pExt;
- HRGN hTmp,hOld,hNew;
- if(pbd = (PBALLDATA)LocalLock(hBall))
- {
- /*
- ** Create old ball object.
- */
- pOrg.x = 0;
- pOrg.y = 0;
- pExt.x = pbd->nWidth;
- pExt.y = pbd->nHeight;
- XFormPoint(&pbd->xForm,&pOrg);
- XFormPoint(&pbd->xForm,&pExt);
- hOld = CreateEllipticRgn(pOrg.x,pOrg.y,pExt.x,pExt.y);
- /*
- ** Create new ball object.
- */
- if(pbd->bNewPosition)
- {
- pbd->bNewPosition = FALSE;
- XFormClear(&pbd->xForm);
- XFormTrans(&pbd->xForm,pbd->xPosition,pbd->yPosition);
- }
- else
- XFormTrans(&pbd->xForm,pbd->xDirection,pbd->yDirection);
- pOrg.x = 0;
- pOrg.y = 0;
- pExt.x = pbd->nWidth;
- pExt.y = pbd->nHeight;
- XFormPoint(&pbd->xForm,&pOrg);
- XFormPoint(&pbd->xForm,&pExt);
- hNew = CreateEllipticRgn(pOrg.x,pOrg.y,pExt.x,pExt.y);
- if(hDC = GetDC(pbd->hWnd))
- {
- hTmp = CreateRectRgn(1,1,2,2);
- CombineRgn(hTmp,hOld,hNew,RGN_DIFF);
- FillRgn(hDC,hTmp,GETCLASSBRUSH(pbd->hWnd));
- hBrush = CreateSolidBrush(pbd->crColor);
- FillRgn(hDC,hNew,hBrush);
- DeleteObject(hBrush);
- ReleaseDC(pbd->hWnd,hDC);
- DeleteObject(hTmp);
- }
- DeleteObject(hOld);
- DeleteObject(hNew);
- LocalUnlock(hBall);
- }
- return;
- }
- BOOL ballGetDimensions(HANDLE hBall, LPPOINT pDimension)
- {
- PBALLDATA pbd;
- BOOL bOK;
- bOK = FALSE;
- if(pbd = (PBALLDATA)LocalLock(hBall))
- {
- pDimension->x = pbd->nWidth;
- pDimension->y = pbd->nHeight;
- bOK = TRUE;
- LocalUnlock(hBall);
- }
- return(bOK);
- }
- BOOL ballSetDimensions(HANDLE hBall, int nWidth, int nHeight)
- {
- PBALLDATA pbd;
- BOOL bOK;
- bOK = FALSE;
- if(pbd = (PBALLDATA)LocalLock(hBall))
- {
- pbd->nWidth = nWidth;
- pbd->nHeight = nHeight;
- bOK = TRUE;
- LocalUnlock(hBall);
- }
- return(bOK);
- }
- BOOL ballGetDirection(HANDLE hBall, LPPOINT pDirection)
- {
- PBALLDATA pbd;
- BOOL bOK;
- bOK = FALSE;
- if(pbd = (PBALLDATA)LocalLock(hBall))
- {
- pDirection->x = pbd->xDirection;
- pDirection->y = pbd->yDirection;
- bOK = TRUE;
- LocalUnlock(hBall);
- }
- return(bOK);
- }
- BOOL ballSetDirection(HANDLE hBall, int xDirection, int yDirection)
- {
- PBALLDATA pbd;
- BOOL bOK;
- bOK = FALSE;
- if(pbd = (PBALLDATA)LocalLock(hBall))
- {
- pbd->xDirection = xDirection;
- pbd->yDirection = yDirection;
- bOK = TRUE;
- LocalUnlock(hBall);
- }
- return(bOK);
- }
- BOOL ballGetPosition(HANDLE hBall, LPPOINT pPosition)
- {
- PBALLDATA pbd;
- BOOL bOK;
- POINT pOrg;
- bOK = FALSE;
- if(pbd = (PBALLDATA)LocalLock(hBall))
- {
- pOrg.x = 0;
- pOrg.y = 0;
- XFormPoint(&pbd->xForm,&pOrg);
- pPosition->x = pOrg.x;
- pPosition->y = pOrg.y;
- bOK = TRUE;
- LocalUnlock(hBall);
- }
- return(bOK);
- }
- BOOL ballSetPosition(HANDLE hBall, int x, int y)
- {
- PBALLDATA pbd;
- BOOL bOK;
- bOK = FALSE;
- if(pbd = (PBALLDATA)LocalLock(hBall))
- {
- pbd->bNewPosition = TRUE;
- pbd->xPosition = x;
- pbd->yPosition = y;
- bOK = TRUE;
- LocalUnlock(hBall);
- }
- return(bOK);
- }