home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
swCHIP 1991 January
/
swCHIP_95-1.bin
/
desktop
/
scrsavr
/
bouncer1
/
bouncer.c
< prev
next >
Wrap
C/C++ Source or Header
|
1995-12-09
|
15KB
|
511 lines
/* BOUNCER.C - ScreenSaverProc(), RegisterDialogClasses(),
* ScreenSaverConfigureDialog() and other support code for
* BOUNCER.
*
* BOUNCER is a sample screen saver application. It bounces a
* bitmap across the display and produces a sound when the
* bitmap image is at the bottom of the screen.
*
* (C) Copyright Microsoft Corp. 1991. All rights reserved.
*
* You have a royalty-free right to use, modify, reproduce and
* distribute the Sample Files (and/or any modified version) in
* any way you find useful, provided that you agree that
* Microsoft has no warranty obligations or liability for any
* Sample Application Files which are modified.
*/
// COPYRIGHT:
//
// (C) Copyright Microsoft Corp. 1992. All rights reserved.
//
// You have a royalty-free right to use, modify, reproduce and
// distribute the Sample Files (and/or any modified version) in
// any way you find useful, provided that you agree that
// Microsoft has no warranty obligations or liability for any
// Sample Application Files which are modified.
#include <windows.h>
#include <mmsystem.h>
#include "bouncer.h"
/* Global used by SCRNSAVE.LIB. Required for all screen savers.
*/
char szAppName[40];
/* Globals specific to BOUNCER.
*/
char szDIBName[] = "BounceDIB";
char szSpeedName[] = "Speed";
char szXPosName[] = "xPosition";
char szYPosName[] = "yPosition";
char szXVelocityName[] = "xVelocity";
char szGravityName[] = "Gravity";
char szSoundName[] = "Sound";
char szDIBNumName[] = "DIBNum";
char szPauseName[] = "Pause at bottom";
char szName[] = "Bounce a bitmap";
/* Externals defined in SCRNSAVE.LIB. Required for all screen savers.
*/
HINSTANCE _cdecl hMainInstance;
HWND _cdecl hMainWindow;
char _cdecl szName[TITLEBARNAMELEN];
char _cdecl szIsPassword[22];
char _cdecl szIniFile[MAXFILELEN];
char _cdecl szScreenSaver[22];
char _cdecl szPassword[16];
char _cdecl szDifferentPW[BUFFLEN];
char _cdecl szChangePW[30];
char _cdecl szBadOldPW[BUFFLEN];
char _cdecl szHelpFile[MAXFILELEN];
char _cdecl szNoHelpMemory[BUFFLEN];
UINT _cdecl MyHelpMessage;
HOOKPROC _cdecl fpMessageFilter;
HBITMAP hbmImage; // image handle
WORD wElapse; // speed parameter
WORD wTimer; // timer id
BOOL bBottom; // TRUE if frog is at bottom of screen
int xPos; // current x position
int yPos; // current y position
int xPosInit; // initial x position
int yPosInit; // initial y position
int xVelocInit; // x initial velocity
int nGravity; // acceleration factor
BOOL bSound; // sound on/off flag
BOOL bPause; // stick at bottom of screen?
BOOL bPassword; // password protected?
HANDLE hresWave; // handle to sound resource
LPSTR lpWave; // pointer to wave resource
/* ScreenSaverProc - Main entry point for screen saver messages.
* This function is required for all screen savers.
*
* Params: Standard window message handler parameters.
*
* Return: The return value depends on the message.
*
* Note that all messages go to the DefScreenSaverProc(), except
* for ones we process.
*/
LONG FAR PASCAL ScreenSaverProc (HWND hWnd, UINT msg, WPARAM wParam, LPARAM
lParam)
{
RECT rc;
static WORD wBottomCount;
switch (msg)
{
case WM_CREATE: // BOUNCER-specific
{
HANDLE hResInfo;
/* Load the strings from the STRINGTABLE
*/
GetIniEntries();
/* Load the initial bounce settings.
*/
GetIniSettings();
/* Load the DIB image we want to use.
*/
hbmImage = LoadBitmap(hMainInstance, szDIBName);
/* Load and lock the sound resource
*/
if (hResInfo = FindResource(hMainInstance, "Sound", "WAVE"))
{
if (hresWave = LoadResource(hMainInstance, hResInfo))
{
lpWave = LockResource(hresWave);
}
}
/* Create a timer to move the image
*/
wTimer = SetTimer(hWnd, ID_TIMER, wElapse, NULL);
xPos = xPosInit;
yPos = yPosInit;
break;
}
case WM_TIMER: // BOUNCER-specific
if (bPause && bBottom)
{
if (++wBottomCount == 10)
{
wBottomCount = 0;
bBottom = FALSE;
}
break;
}
/* Move the image around a bit
*/
MoveImage(hWnd);
break;
case WM_DESTROY: // BOUNCER-specific
/* Destroy any objects we created
*/
if (hbmImage)
DeleteObject(hbmImage);
if (wTimer)
KillTimer(hWnd, ID_TIMER);
sndPlaySound(NULL, 0);
/*s-*/ if( lpWave ) UnlockResource(hresWave); /*s+*/
if (hresWave)
FreeResource(hresWave);
break;
case WM_ERASEBKGND:
GetClientRect(hWnd, &rc);
FillRect((HDC)wParam, &rc, (HBRUSH)GetStockObject(BLACK_BRUSH));
return 0L;
default:
break;
}
return DefScreenSaverProc(hWnd, msg, wParam, lParam);
}
/* RegisterDialogClasses -- Entry point for registering window
* classes required by configuration dialog box.
*
* Params: hWnd -- Handle to window
*
* Return: None
*/
BOOL RegisterDialogClasses (HINSTANCE hInst)
{
return TRUE;
}
/* ScreenSaverConfigureDialog -- Dialog box function for configuration
* dialog.
*
* Params: hWnd -- Handle to window
*
* Return: None
*/
BOOL FAR PASCAL ScreenSaverConfigureDialog (HWND hDlg, UINT msg, WPARAM wParam,
LPARAM lParam)
{
static HWND hIDOK;
static HWND hSetPassword;
switch (msg)
{
case WM_INITDIALOG: // BOUNCER-specific
GetIniEntries();
GetIniSettings();
SetDlgItemInt(hDlg, ID_SPEED, wElapse, FALSE);
SetDlgItemInt(hDlg, ID_XPOS, xPosInit, TRUE);
SetDlgItemInt(hDlg, ID_YPOS, yPosInit, TRUE);
SetDlgItemInt(hDlg, ID_VELOCITY, xVelocInit, TRUE);
SetDlgItemInt(hDlg, ID_GRAVITY, nGravity, TRUE);
SendDlgItemMessage(hDlg, ID_SOUND, BM_SETCHECK, bSound, NULL);
SendDlgItemMessage(hDlg, ID_PAUSE, BM_SETCHECK, bPause, NULL);
SendDlgItemMessage(hDlg, ID_PASSWORDPROTECTED, BM_SETCHECK, bPassword,
NULL);
hSetPassword = GetDlgItem(hDlg, ID_SETPASSWORD);
EnableWindow(hSetPassword, bPassword);
hIDOK = GetDlgItem(hDlg, IDOK);
return TRUE;
case WM_COMMAND: // BOUNCER-specific
switch (wParam)
{
case IDOK:
wElapse = GetDlgItemInt(hDlg, ID_SPEED, NULL, FALSE);
xPosInit = GetDlgItemInt(hDlg, ID_XPOS, NULL, TRUE);
yPosInit = GetDlgItemInt(hDlg, ID_YPOS, NULL, TRUE);
xVelocInit = GetDlgItemInt(hDlg, ID_VELOCITY, NULL, TRUE);
nGravity = GetDlgItemInt(hDlg, ID_GRAVITY, NULL, TRUE);
bSound = IsDlgButtonChecked(hDlg, ID_SOUND);
bPause = IsDlgButtonChecked(hDlg, ID_PAUSE);
bPassword = IsDlgButtonChecked(hDlg, ID_PASSWORDPROTECTED);
WriteProfileInt(szAppName, szSpeedName, wElapse);
WriteProfileInt(szAppName, szXPosName, xPosInit);
WriteProfileInt(szAppName, szYPosName, yPosInit);
WriteProfileInt(szAppName, szXVelocityName, xVelocInit);
WriteProfileInt(szAppName, szGravityName, nGravity);
WriteProfileInt(szAppName, szSoundName, bSound);
WriteProfileInt(szAppName, szPauseName, bPause);
WriteProfileInt(szAppName, szIsPassword, bPassword);
EndDialog(hDlg, TRUE);
return TRUE;
case IDCANCEL:
EndDialog(hDlg, FALSE);
return TRUE;
case ID_SETPASSWORD:
{
FARPROC fpDialog;
if ((fpDialog = MakeProcInstance(DlgChangePassword, hMainInstance)) ==
NULL)
return FALSE;
DialogBox(hMainInstance, MAKEINTRESOURCE(DLG_CHANGEPASSWORD), hDlg,
fpDialog);
FreeProcInstance(fpDialog);
SendMessage(hDlg, WM_NEXTDLGCTL, hIDOK, 1l);
break;
}
case ID_PASSWORDPROTECTED:
bPassword ^= 1;
CheckDlgButton(hDlg, wParam, bPassword);
EnableWindow(hSetPassword, bPassword);
break;
case ID_HELP:
DoHelp:
#if 0
bHelpActive=WinHelp(hDlg, szHelpFile, HELP_CONTEXT, IDH_DLG_BOUNCER);
if (!bHelpActive)
MessageBox(hDlg, szNoHelpMemory, szName, MB_OK);
#else
MessageBox(hDlg, "Insert your call to WinHelp() here.", szName, MB_OK)
;
#endif
break;
}
break;
default:
if (msg == MyHelpMessage) // Context sensitive help msg.
goto DoHelp;
}
return FALSE;
}
/* THE REST OF THIS FILE IS SPECIFIC TO BOUNCER.
*
* Replace it with your own screen saver code.
*/
/* GetIniSettings -- Get initial bounce settings from WIN.INI
*
* Params: hWnd -- Handle to window
*
* Return: None
*/
static void GetIniSettings ()
{
wElapse = GetPrivateProfileInt(szAppName, szSpeedName, DEF_SPEED, szIniFile)
;
xPosInit = GetPrivateProfileInt(szAppName, szXPosName, DEF_INIT_XPOS,
szIniFile);
yPosInit = GetPrivateProfileInt(szAppName, szYPosName, DEF_INIT_YPOS,
szIniFile);
xVelocInit = GetPrivateProfileInt(szAppName, szXVelocityName, DEF_INIT_VELOC
, szIniFile);
nGravity = GetPrivateProfileInt(szAppName, szGravityName, DEF_INIT_GRAVITY,
szIniFile);
bSound = GetPrivateProfileInt(szAppName, szSoundName, DEF_SOUND, szIniFile);
bPause = GetPrivateProfileInt(szAppName, szPauseName, DEF_PAUSE, szIniFile);
bPassword = GetPrivateProfileInt(szAppName, szIsPassword, FALSE, szIniFile);
}
/* MoveImage -- Move image around the screen
*
* Params: hWnd -- Handle to window
*
* Return: None
*/
static void MoveImage (HWND hWnd)
{
// static int xPos = 10000; // Current x value (force a reset)
// static int yPos = 0; // Current y value
static int yVeloc = 0; // Current y velocity
int xPosOld, yPosOld;
HDC hDC; // Handle to our window DC
HDC hMemDC; // Handle to a memory DC
BITMAP bm; // Bitmap info
HBITMAP hbmOld;
RECT rcWnd, rcFill;
/* Get window size
*/
GetClientRect(hWnd, &rcWnd);
/* Get bitmap size
*/
GetObject(hbmImage, sizeof(bm), (LPSTR)&bm);
/* Update x- and y-position values
*/
xPosOld = xPos;
yPosOld = yPos;
yVeloc += nGravity;
xPos += xVelocInit;
yPos += yVeloc;
/* If we're at the bottom, BOUNCE!
*/
if ((yPos + bm.bmHeight > rcWnd.bottom) && (yVeloc > 0))
{
yVeloc = -yVeloc; // Reverse directions
if (bSound && lpWave) // Boing!!!
{
// do the multimedia bit
sndPlaySound(lpWave, SND_ASYNC | SND_MEMORY | SND_NODEFAULT);
}
bBottom = TRUE;
}
/* If we're off the right of the screen, or off the bottom of the
* screen, start over at beginning position and zero y-velocity.
*/
if ((xPos > rcWnd.right) || (yPos > rcWnd.bottom))
{
yVeloc = 0;
xPos = xPosInit;
yPos = yPosInit;
}
/* Get a DC to our window. Create a compatible memory
* DC and select our image bitmap into it so we can blit
* it to the main window DC
*/
hDC = GetDC(hWnd);
hMemDC = CreateCompatibleDC(hDC);
hbmOld = SelectObject(hMemDC, hbmImage);
if (hbmOld)
{
/* Blit the image in the new position
*/
BitBlt(hDC, // dest DC
xPos, yPos, // dest origin
bm.bmWidth, bm.bmHeight, // dest extents
hMemDC, // src DC
0, 0, // src origin
SRCCOPY); // ROP code
SelectObject(hMemDC, hbmOld);
/* Tidy up where the old image was by filling exposed bits with
* the background color
*
* This code assumes the image always moves to the right
*/
rcFill.left = xPosOld; // Left bits
rcFill.top = yPosOld;
rcFill.right = xPos;
rcFill.bottom = rcFill.top + bm.bmHeight;
FillRect(hDC, &rcFill, GetStockObject(BLACK_BRUSH));
rcFill.right = rcFill.left + bm.bmWidth; // Top or bottom bits
if (yPos > yPosOld)
{
rcFill.bottom = yPos; // Top bits
}
else
{
rcFill.top = yPos + bm.bmHeight; // Bottom bits
rcFill.bottom = yPosOld + bm.bmHeight;
}
FillRect(hDC, &rcFill, GetStockObject(BLACK_BRUSH));
}
DeleteDC(hMemDC);
ReleaseDC(hWnd, hDC);
}
/* WriteProfileInt - Write an unsigned integer value to CONTROL.INI.
*
* Params: name - szSection - [section] name in .INI file
* szKey - key= in .INI file
* i - value for key above
*
* Return: None
*/
static void WriteProfileInt (LPSTR szSection, LPSTR szKey, int i)
{
char achBuf[40];
/* write out as unsigned because GetPrivateProfileInt() can't
* cope with signed values!
*/
wsprintf(achBuf, "%u", i);
WritePrivateProfileString(szSection, szKey, achBuf, szIniFile);
}
void GetIniEntries (void)
{
//Load Common Strings from stringtable...
LoadString(hMainInstance, idsIsPassword, szIsPassword, 22);
LoadString(hMainInstance, idsIniFile, szIniFile, MAXFILELEN);
LoadString(hMainInstance, idsScreenSaver, szScreenSaver, 22);
LoadString(hMainInstance, idsPassword, szPassword, 16);
LoadString(hMainInstance, idsDifferentPW, szDifferentPW, BUFFLEN);
LoadString(hMainInstance, idsChangePW, szChangePW, 30);
LoadString(hMainInstance, idsBadOldPW, szBadOldPW, 255);
LoadString(hMainInstance, idsHelpFile, szHelpFile, MAXFILELEN);
LoadString(hMainInstance, idsNoHelpMemory, szNoHelpMemory, BUFFLEN);
}