home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
World of Shareware - Software Farm 2
/
wosw_2.zip
/
wosw_2
/
CPROG
/
SS14.ZIP
/
SS.C
< prev
next >
Wrap
C/C++ Source or Header
|
1991-01-24
|
23KB
|
639 lines
/****************************************************************************
*
* FILE: SS.C
*
* DESCRIPTION: Windows 3.0 Screen Saver Utility. This version supports
* activation time setup via the system menu. Activation
* time is stored in the Win.Ini initialization file so that
* the activation time will be restored every time this app-
* lication is run.
*
* This software is hereby placed in the public domain.
* Use and abuse it at your own risk!
*
*
* AUTHOR: Tom Wheeler
* 31294 Morlock
* Livonia, Mich. 48152
* [72037,1742]
*
*****************************************************************************
*
* DATE DESCRIPTION
* ---------- -----------------------------------------------------------
* 10/11/90 Initial Development
* 11/02/90 Better activation time control, mouse detection added
* 11/08/90 Mouse capture problems resolved
* 11/20/90 Improved mouse capturing functionality (not perfect yet,
* however).
* 01/24/91 Eliminated mouse capturing altogether in favor of sub-
* classing the Active window to determine mouse activity.
*
****************************************************************************/
#include <windows.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include "ss.h"
/********************************* CONSTANTS *******************************/
#define VERSIONID "Version 1.4"
#define ONE_MINUTE (WORD)60000 /* 60 Second Timer for Activation */
#define DRAW_TIME (WORD)3000 /* 3 Second Timer for Screen Update */
#define MOUSE_TIME (WORD)1000 /* 1 Second Mouse Capture Timer */
#define MOUSE_COUNT 5 /* Deactivation Mouse Counter */
#define DRAW_TIMER 1 /* Screen Update Timer ID */
#define ACTIVATE_TIMER 2 /* Activation Timer ID */
#define MOUSE_TIMER 3 /* Mouse Capture Timer ID */
/* Macro to get a random integer within a specified range */
#define getrandom( min, max ) ((rand() % (int)(((max)+1) - (min))) + (min))
/********************************* VARIABLES *******************************/
char szAppName[] = "Screen Saver";
char szChildClass[] = "Screen Save Child";
BOOL bShow = FALSE;
HANDLE hInst = NULL;
HWND hWndMain = NULL;
HWND hWndChild = NULL;
HWND hFocus = NULL;
HBITMAP hBitmap = NULL;
WORD wDrawTimer = 0;
WORD wActivateTimer = 0;
WORD wMouseTimer = 0;
WORD wTimeOut = 1;
WORD wTimeCount = 0;
int iOldX=0,iOldY = 0;
BITMAP Drawbm = {0};
RECT DrawRect = {0};
FARPROC lpfnOldProc = (FARPROC)NULL;/* subclassed window proc */
FARPROC lpfnNewProc = (FARPROC)NULL;/* subclassing window proc */
/********************************* FUNCTIONS *******************************/
/****************************************************************************
*
* void CenterWindow(HWND hWnd)
*
* DESCRIPTION: Centers a window on the screen
*
* INPUT: hWnd - Handle to window to be centered
*
* OUTPUT: N/A
*
****************************************************************************/
void CenterWindow(HWND hWnd)
{
int iX,iY,iNewX,iNewY;
RECT rect;
iX = GetSystemMetrics(SM_CXSCREEN);
iY = GetSystemMetrics(SM_CYSCREEN);
GetWindowRect(hWnd,(LPRECT)&rect);
iNewX = (iX/2)-((rect.right-rect.left)/2);
iNewY = (iY/2)-((rect.bottom-rect.top)/2);
SetWindowPos(hWnd,NULL,iNewX,iNewY,rect.right-rect.left,
rect.bottom-rect.top,SWP_NOZORDER);
}
/****************************************************************************
*
* BOOL FAR PASCAL AboutDlgProc(HWND hDlg,int iMessage,WORD wParam,
* LONG lParam)
*
* DESCRIPTION: About Dialog Box Proc
*
* INPUT: hDlg - Handle to Dialog Box
* iMessage - Dialog Box message
* wParam
* lParam - Standard Windows message parameters
* Called externally from WINDOWS - Exported Function
*
* OUTPUT: N/A
*
****************************************************************************/
BOOL FAR PASCAL AboutDlgProc(HWND hDlg,int iMessage,WORD wParam,LONG lParam)
{
char szTemp[80];
switch (iMessage) {
case WM_COMMAND:
EndDialog(hDlg,TRUE);
/* fall through */
case WM_INITDIALOG:
strcpy(szTemp,VERSIONID);
sprintf(szTemp,"%s %s %s",VERSIONID,__DATE__,__TIME__);
SetDlgItemText(hDlg,IDD_PGMVERSION,(LPSTR)szTemp);
CenterWindow(hDlg);
return(TRUE);
default:
return(FALSE);
}
return(FALSE);
}
/****************************************************************************
*
* BOOL FAR PASCAL TimeEditDlgProc(HWND hDlg,int iMessage,WORD wParam,
* LONG lParam)
*
* DESCRIPTION: Screen Save Time Edit Dialog Box Proc
*
* INPUT: hDlg - Handle to Dialog Box
* iMessage - Dialog Box message
* wParam
* lParam - Standard Windows message parameters
* Called externally from WINDOWS - Exported Function
*
* OUTPUT: N/A
*
****************************************************************************/
BOOL FAR PASCAL TimeEditDlgProc(HWND hDlg,int iMessage,WORD wParam,
LONG lParam)
{
BOOL bTransFlag;
WORD wVal;
char szTime[10];
switch (iMessage) {
case WM_COMMAND:
switch(wParam) {
case IDD_SAVE:
wVal = GetDlgItemInt(hDlg,IDD_TIMEEDIT,(BOOL FAR *)&bTransFlag,
FALSE);
if((!bTransFlag) || (wVal < 1)) {
MessageBeep(0);
sprintf(szTime,"%d",wTimeOut);
SetDlgItemText(hDlg,IDD_TIMEEDIT,(LPSTR)szTime);
}
else {
wTimeOut = wVal;
sprintf(szTime,"%d",wTimeOut);
WriteProfileString((LPSTR)"screen save",(LPSTR)"activate",
(LPSTR)szTime);
EndDialog(hDlg,FALSE);
}
break;
case IDD_CANCEL:
EndDialog(hDlg,FALSE);
break;
}
break;
case WM_INITDIALOG:
sprintf(szTime,"%d",wTimeOut);
SetDlgItemText(hDlg,IDD_TIMEEDIT,(LPSTR)szTime);
CenterWindow(hDlg);
return(TRUE);
default:
return(FALSE);
}
return(FALSE);
}
/****************************************************************************
*
* FUNCTION : DrawBitmap(HDC hdc,int x,int y,HBITMAP hbm,DWORD rop)
*
* PURPOSE : Draws bitmap <hbm> at the specifed position in DC <hdc>
*
* RETURNS : Return value of BitBlt()
*
****************************************************************************/
BOOL DrawBitmap(HDC hdc,int x,int y,HBITMAP hbm,DWORD rop)
{
HDC hdcBits;
BITMAP bm;
BOOL f;
if (!hdc || !hbm)
return FALSE;
hdcBits = CreateCompatibleDC(hdc);
GetObject(hbm,sizeof(BITMAP),(LPSTR)&bm);
SelectObject(hdcBits,hbm);
f = BitBlt(hdc,x,y,bm.bmWidth,bm.bmHeight,hdcBits,0,0,rop);
DeleteDC(hdcBits);
return f;
}
/****************************************************************************
*
* long FAR PASCAL WndProc(HWND hWnd,int iMessage,WORD wParam,LONG lParam)
* LONG lParam)
*
* DESCRIPTION: ScreenSave Main Window Proc
*
* INPUT: hWnd - Handle to Window
* iMessage - Dialog Box message
* wParam
* lParam - Standard Windows message parameters
* Called externally from WINDOWS - Exported Function
*
* OUTPUT: N/A
*
****************************************************************************/
long FAR PASCAL WndProc(HWND hWnd,int iMessage,WORD wParam,LONG lParam)
{
FARPROC lpfn;
switch(iMessage) {
case WM_SYSCOMMAND:
switch(wParam) {
case IDM_ABOUT:
lpfn = MakeProcInstance((FARPROC)AboutDlgProc,hInst);
DialogBox(hInst,"ABOUTDLGBOX",hWnd,lpfn);
FreeProcInstance(lpfn);
break;
case IDM_SETTIME:
lpfn = MakeProcInstance((FARPROC)TimeEditDlgProc,hInst);
DialogBox(hInst,"TIMEVALINPUT",hWnd,lpfn);
FreeProcInstance(lpfn);
break;
default:
return DefWindowProc(hWnd,iMessage,wParam,lParam);
break;
}
break;
case WM_QUERYOPEN:
break;
case WM_DESTROY:
if(wDrawTimer) {
KillTimer(hWndChild,DRAW_TIMER);
wDrawTimer = 0;
}
if(wActivateTimer) {
KillTimer(hWndChild,ACTIVATE_TIMER);
wActivateTimer = 0;
}
if(wMouseTimer) {
KillTimer(hWndChild,MOUSE_TIMER);
wActivateTimer = 0;
if((lpfnOldProc != (FARPROC)NULL) &&
(lpfnNewProc != (FARPROC)NULL)) {
SetWindowLong(hFocus,GWL_WNDPROC,(LONG)lpfnOldProc);
FreeProcInstance(lpfnNewProc);
lpfnOldProc = (FARPROC)NULL;
lpfnNewProc = (FARPROC)NULL;
}
}
PostQuitMessage(0);
break;
default:
return DefWindowProc(hWnd,iMessage,wParam,lParam);
break;
}
return 0L;
}
/****************************************************************************
* LONG FAR ActiveFilterProc(hWnd,iMessage,wParam,lParam)
*
* Description: Subclassing proc to filter mouse activity in the currently
* active window.
*
* Input: hWnd - Handle to Window
* iMessage - Dialog Box message
* wParam
* lParam - Standard Windows message parameters
* Called externally from WINDOWS - Exported Function
*
* Output: Chains to subclassed proc after filtering mouse activity.
* Posts a message to "ChildWndProc" to indicate the detection
* of any filtered messages.
****************************************************************************/
LONG FAR PASCAL ActiveFilterProc(HWND hWnd,WORD iMessage,WORD wParam,
LONG lParam)
{
switch(iMessage) {
case WM_SETCURSOR:
case WM_NCHITTEST:
PostMessage(hWndChild,WM_HOOKKEY,0,0L);
break;
}
return CallWindowProc(lpfnOldProc,hWnd,iMessage,wParam,lParam);
}
/****************************************************************************
*
* long FAR PASCAL ChildWndProc(HWND hWnd,int iMessage,WORD wParam,
* LONG lParam)
*
* DESCRIPTION: ScreenSave Child Window Proc - Responsible for most of the
* active screen save functions
*
* INPUT: hWnd - Handle to Window
* iMessage - Dialog Box message
* wParam
* lParam - Standard Windows message parameters
* Called externally from WINDOWS - Exported Function
*
* OUTPUT: N/A
*
****************************************************************************/
long FAR PASCAL ChildWndProc(HWND hWnd,int iMessage,WORD wParam,LONG lParam)
{
HDC hDC;
HWND hTest;
PAINTSTRUCT ps;
static int iMcount = MOUSE_COUNT;
static HCURSOR hCursor;
switch(iMessage) {
case WM_HOOKKEY:
/* This message is sent by "SSHOOK.DLL" when it detects any
* keyboard activity. It is also sent by "ActiveFilterProc"
* when any mouse activity is detected in the currently active
* window.
*/
goto Bypass;
case WM_SETCURSOR:
if(bShow) {
/* If the screen is blanked, keep a count of mouse activity and
* only deactivate after a specified number of messages. This
* provides a littly hysteresis for mouse activity.
*/
if(iMcount) {
--iMcount;
break;
}
}
goto Bypass;
case WM_LBUTTONDOWN:
case WM_LBUTTONUP:
case WM_RBUTTONDOWN:
case WM_RBUTTONUP:
/* process all mouse button activity */
Bypass:
if((wActivateTimer =
SetTimer(hWnd,ACTIVATE_TIMER,ONE_MINUTE,NULL)) == 0) {
MessageBox(hWndMain,"No More System Timers!",
szAppName,MB_OK | MB_ICONEXCLAMATION);
PostQuitMessage(0);
}
if(bShow) {
iMcount = MOUSE_COUNT;
SetCursor(hCursor);
ShowWindow(hWndChild,SW_HIDE);
iOldX = (GetSystemMetrics(SM_CXSCREEN) - Drawbm.bmWidth) / 2;
iOldY = (GetSystemMetrics(SM_CYSCREEN) - Drawbm.bmHeight) / 2;
if(wDrawTimer) {
KillTimer(hWnd,DRAW_TIMER);
wDrawTimer = 0;
wTimeCount = 0;
}
}
bShow = FALSE;
break;
case WM_TIMER:
switch(wParam) {
case DRAW_TIMER:
/* This timer indicates that it is time to move the icon
* on the saved screen
*/
if(bShow) {
hDC = GetDC(hWnd);
DrawBitmap(hDC,iOldX,iOldY,hBitmap,BLACKNESS);
iOldX = getrandom(0,(DrawRect.right-Drawbm.bmWidth));
iOldY = getrandom(0,(DrawRect.bottom-Drawbm.bmHeight));
DrawBitmap(hDC,iOldX,iOldY,hBitmap,SRCCOPY);
ReleaseDC(hWnd,hDC);
}
break;
case ACTIVATE_TIMER:
/* This timer indicates that the specified activation time
* has expired. Screen save initialization is performed and
* the screen is blanked (ie. the child window is displayed.)
*/
if(!bShow) {
wTimeCount++;
if(wTimeCount == wTimeOut) {
if((wDrawTimer =
SetTimer(hWnd,DRAW_TIMER,DRAW_TIME,NULL)) == 0) {
MessageBox(hWndMain,"No More System Timers!",
szAppName,MB_OK | MB_ICONEXCLAMATION);
PostQuitMessage(0);
}
hCursor = SetCursor(NULL);
ShowWindow(hWndChild,SW_SHOWNORMAL);
bShow = TRUE;
}
}
break;
case MOUSE_TIMER:
if(wMouseTimer && !bShow) {
/* Sub-class the active window and filter for signs of
* mouse activity.
*/
if((hTest = GetActiveWindow()) != NULL) {
if(hTest != hFocus) {
/* onlu sub-class if the active window has changed */
if((lpfnOldProc != (FARPROC)NULL) &&
(lpfnNewProc != (FARPROC)NULL)) {
SetWindowLong(hFocus,GWL_WNDPROC,(LONG)lpfnOldProc);
FreeProcInstance(lpfnNewProc);
}
hFocus = hTest;
lpfnOldProc = (FARPROC)GetWindowLong(hFocus,
GWL_WNDPROC);
lpfnNewProc =
MakeProcInstance((FARPROC)ActiveFilterProc,
hInst);
if((lpfnOldProc != (FARPROC)NULL) &&
(lpfnNewProc != (FARPROC)NULL)) {
SetWindowLong(hFocus,GWL_WNDPROC,
(LONG)lpfnNewProc);
}
}
}
}
break;
}
break;
case WM_PAINT:
/* displays the screen save icon */
hDC = BeginPaint(hWnd,&ps);
DrawBitmap(hDC,iOldX,iOldY,hBitmap,SRCCOPY);
EndPaint(hWnd,&ps);
break;
case WM_CREATE:
/* initialization code for the screen saver blanking window */
srand((unsigned)time(NULL));
if((hBitmap = LoadBitmap(hInst,"SaveScreen")) == NULL) {
MessageBox(hWndMain,"Could Not Create Bitmap!",
szAppName,MB_OK | MB_ICONEXCLAMATION);
PostQuitMessage(0);
}
if((wActivateTimer =
SetTimer(hWnd,ACTIVATE_TIMER,ONE_MINUTE,NULL)) == 0) {
MessageBox(hWndMain,"No More System Timers!",
szAppName,MB_OK | MB_ICONEXCLAMATION);
PostQuitMessage(0);
}
if((wMouseTimer =
SetTimer(hWnd,MOUSE_TIMER,MOUSE_TIME,NULL)) == 0) {
MessageBox(hWndMain,"No More System Timers!",
szAppName,MB_OK | MB_ICONEXCLAMATION);
PostQuitMessage(0);
}
GetClientRect(hWnd,&DrawRect);
GetObject(hBitmap,sizeof(BITMAP),(LPSTR)&Drawbm);
iOldX = (GetSystemMetrics(SM_CXSCREEN) - Drawbm.bmWidth) / 2;
iOldY = (GetSystemMetrics(SM_CYSCREEN) - Drawbm.bmHeight) / 2;
InitHook(hWnd);
break;
default:
return DefWindowProc(hWnd,iMessage,wParam,lParam);
break;
}
return 0L;
}
/****************************************************************************
*
* int far PASCAL WinMain(HANDLE hInstance, HANDLE hPrevInstance,
* LPSTR lpszCmdLine, int nCmdShow);
*
* DESCRIPTION: ScreenSave Main Function
*
* INPUT: N/A
*
* OUTPUT: N/A
*
****************************************************************************/
int PASCAL WinMain(HANDLE hInstance, HANDLE hPrevInstance,
LPSTR lpszCmdLine, int nCmdShow)
{
MSG msg;
WNDCLASS wc;
HANDLE hMenu;
hInst = hInstance;
if( !hPrevInstance )
{
/* client window class */
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = WndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInstance;
wc.hIcon = LoadIcon(hInstance,"SS");
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
wc.hbrBackground = GetStockObject(BLACK_BRUSH);
wc.lpszMenuName = szAppName;
wc.lpszClassName = szAppName;
if( !RegisterClass( &wc ) )
return NULL;
wc.style = CS_HREDRAW | CS_VREDRAW;
wc.lpfnWndProc = ChildWndProc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hInstance = hInstance;
wc.hIcon = NULL;
wc.hCursor = NULL;
wc.hbrBackground = GetStockObject (BLACK_BRUSH);
wc.lpszMenuName = NULL;
wc.lpszClassName = szChildClass;
if( !RegisterClass( &wc ) )
return NULL;
}
else {
MessageBox(NULL,(LPSTR)"Can't start more than one copy of Screen Saver!",
(LPSTR)szAppName,MB_OK | MB_ICONSTOP);
return TRUE;
}
/* create the main appplication window */
hWndMain = CreateWindow(szAppName, /* Window class name */
szAppName, /* window caption */
WS_OVERLAPPEDWINDOW, /* window style */
CW_USEDEFAULT, /* initial x (horiz) position */
CW_USEDEFAULT, /* initial y (vert) position */
CW_USEDEFAULT, /* initial x size */
CW_USEDEFAULT, /* initial y size */
NULL, /* parent window handle */
NULL, /* window menu handle */
hInstance, /* program instance handle */
NULL); /* create parameters */
/* create the child screen saver window */
hWndChild = CreateWindow(szChildClass, /* window class name */
NULL, /* window caption */
WS_POPUP, /* window style */
0, /* initial x position */
0, /* initial y position */
GetSystemMetrics(SM_CXSCREEN), /* initial x size */
GetSystemMetrics(SM_CYSCREEN), /* initial y size */
NULL, /* parent window handle */
NULL, /* window menu handle */
hInstance, /* program instance handle */
NULL) ; /* create parameters */
/* Rearrange the system menu to suit this programs functionality */
hMenu = GetSystemMenu(hWndMain,FALSE);
DeleteMenu(hMenu,0,MF_BYPOSITION);
DeleteMenu(hMenu,1,MF_BYPOSITION);
DeleteMenu(hMenu,1,MF_BYPOSITION);
DeleteMenu(hMenu,1,MF_BYPOSITION);
AppendMenu(hMenu,MF_SEPARATOR,NULL,NULL);
AppendMenu(hMenu,MF_STRING | MF_ENABLED,IDM_SETTIME,"&Time");
AppendMenu(hMenu,MF_SEPARATOR,NULL,NULL);
AppendMenu(hMenu,MF_STRING | MF_ENABLED,IDM_ABOUT,"&About ...");
/* Recover the saved activation time from WIN.INI. If none, create a
* default activation time of 10 minutes.
*/
wTimeOut = GetProfileInt((LPSTR)"screen save",(LPSTR)"activate",0);
if(wTimeOut == 0) {
WriteProfileString((LPSTR)"screen save",(LPSTR)"activate",(LPSTR)"10");
wTimeOut = 10;
}
/* display the main window iconic */
ShowWindow(hWndMain,SW_SHOWMINNOACTIVE);
UpdateWindow(hWndMain); /* sends WM_PAINT message */
/* Display the screen save window as hidden. It is unhidden only
* upon activation.
*/
ShowWindow(hWndChild,SW_HIDE); /* forces WM_CREATE message */
UpdateWindow(hWndChild); /* sends WM_PAINT message */
while(GetMessage(&msg,NULL,NULL,NULL))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}