home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: 10 Tools
/
10-Tools.zip
/
sftick.zip
/
adv
/
contain
/
CONTAIN3.C
< prev
next >
Wrap
Text File
|
1994-05-05
|
22KB
|
675 lines
#define INCL_WINFRAMEMGR
#define INCL_WINMENUS
#define INCL_WINPOINTERS
#define INCL_WINSTDCNR
#define INCL_WINSYS
#define INCL_WINWINDOWMGR
#include <os2.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include "CONTAIN3.H"
#define CLS_CLIENT "SampleClass"
#define MAX_RECORDS 10
//----------------------------------------------------
// For the GA 2.0 toolkit, CRA_SOURCE is not defined,
// but it should be.
//----------------------------------------------------
#ifndef CRA_SOURCE
#define CRA_SOURCE 0x00004000L
#endif
typedef struct _CLIENTDATA {
HWND hwndCnr ;
HPOINTER hptrIcon ;
HWND hwndMenu ;
BOOL bCnrSelected ;
} CLIENTDATA, *PCLIENTDATA ;
typedef struct _RECORDINFO {
MINIRECORDCORE mrcStd ;
BOOL bEmphasized ;
} RECORDINFO, *PRECORDINFO ;
MRESULT EXPENTRY clientWndProc ( HWND hwndClient,
ULONG ulMsg,
MPARAM mpParm1,
MPARAM mpParm2 ) ;
CHAR *pRecordTitles[] = {"KLetter",
"BLetter",
"ZLetter",
"OOOOOOOO",
"11111111",
"Panov",
"Woo",
"Watts",
"Art of OS/2",
"Hello, World!" } ;
/* record initalization function */
VOID initRecordInfo ( PCLIENTDATA pcdData,
PRECORDINFO psiRecord,
USHORT usIndex ) ;
/* sort Routine */
SHORT pfnSortRecords( PMINIRECORDCORE pmr1,
PMINIRECORDCORE pmr2,
PVOID pStorage) ;
/* routine to turn on and off emphasis */
VOID emphasizeRecs ( HWND hwndCnr, BOOL bEmphasize ) ;
/* routine to free all the container memory */
VOID freeCnrInfo ( HWND hwndCnr ) ;
INT main ( VOID )
{
HAB habAnchor ;
HMQ hmqQueue ;
ULONG ulFlags ;
HWND hwndFrame ;
QMSG qmMsg ;
/* basic PM stuff */
habAnchor = WinInitialize ( 0 ) ;
hmqQueue = WinCreateMsgQueue ( habAnchor, 0 ) ;
WinRegisterClass ( habAnchor,
CLS_CLIENT,
clientWndProc,
0,
sizeof ( PVOID )) ;
ulFlags = FCF_SIZEBORDER | FCF_TITLEBAR |
FCF_TASKLIST | FCF_SHELLPOSITION |
FCF_SYSMENU ;
hwndFrame = WinCreateStdWindow ( HWND_DESKTOP,
WS_VISIBLE,
&ulFlags,
CLS_CLIENT,
"Container Sample",
0,
NULLHANDLE,
RES_CLIENT,
NULL ) ;
if ( hwndFrame ) {
while ( WinGetMsg ( habAnchor, &qmMsg, NULLHANDLE, 0, 0 ))
WinDispatchMsg ( habAnchor, &qmMsg ) ;
WinDestroyWindow ( hwndFrame ) ;
} /* endif */
WinDestroyMsgQueue ( hmqQueue ) ;
WinTerminate ( habAnchor ) ;
return 0 ;
}
MRESULT EXPENTRY clientWndProc ( HWND hwndClient,
ULONG ulMsg,
MPARAM mpParm1,
MPARAM mpParm2 )
{
PCLIENTDATA pcdData ;
pcdData = ( PCLIENTDATA ) WinQueryWindowPtr ( hwndClient, 0 ) ;
switch ( ulMsg ) {
case WM_CREATE:
{
MENUITEM miItem ;
ULONG ulStyle ;
ULONG ulExtra ;
RECORDINSERT riRecord ;
PRECORDINFO psiRecords ;
PRECORDINFO psiHeadRecord ;
USHORT usIndex1 ;
/* allocate window word data */
pcdData = ( PCLIENTDATA ) malloc ( sizeof ( CLIENTDATA ));
/* error checking */
if ( pcdData == NULL ) {
WinAlarm ( HWND_DESKTOP, WA_ERROR ) ;
WinMessageBox ( HWND_DESKTOP,
HWND_DESKTOP,
"No memory is available",
"Error",
0,
MB_ICONEXCLAMATION | MB_OK ) ;
return MRFROMSHORT ( TRUE ) ;
} /* endif */
/* assign window word to client window */
WinSetWindowPtr ( hwndClient, QWL_USER, pcdData ) ;
pcdData->hwndCnr = NULLHANDLE ;
pcdData->hptrIcon = NULLHANDLE ;
pcdData->hwndMenu = NULLHANDLE ;
pcdData->bCnrSelected = FALSE ;
pcdData->hwndCnr = WinCreateWindow (
hwndClient,
WC_CONTAINER,
"",
CCS_MINIRECORDCORE |
CCS_EXTENDSEL |
WS_VISIBLE,
0,
0,
0,
0,
hwndClient,
HWND_TOP,
WND_CONTAINER,
NULL,
NULL ) ;
/* error checking */
if ( pcdData->hwndCnr == NULLHANDLE ) {
free ( pcdData ) ;
WinAlarm ( HWND_DESKTOP, WA_ERROR ) ;
WinMessageBox ( HWND_DESKTOP,
HWND_DESKTOP,
"Cannot create container",
"Error",
0,
MB_ICONEXCLAMATION | MB_OK ) ;
return MRFROMSHORT ( TRUE ) ;
} /* endif */
/* load icon and popup menu */
pcdData->hptrIcon = WinLoadPointer ( HWND_DESKTOP,
NULLHANDLE,
ICO_ITEM ) ;
pcdData->hwndMenu = WinLoadMenu ( hwndClient,
NULLHANDLE,
RES_CLIENT ) ;
/* what is the menuitem window handle for the VIEW */
/* submenu ? */
WinSendMsg ( pcdData->hwndMenu,
MM_QUERYITEM,
MPFROM2SHORT ( M_VIEWS, TRUE ) ,
MPFROMP ( &miItem )) ;
/* change menu style to conditional cascade */
ulStyle = WinQueryWindowULong ( miItem.hwndSubMenu,
QWL_STYLE ) ;
ulStyle |= MS_CONDITIONALCASCADE ;
WinSetWindowULong ( miItem.hwndSubMenu,
QWL_STYLE,
ulStyle ) ;
/* set default to icon view */
WinSendMsg ( miItem.hwndSubMenu,
MM_SETDEFAULTITEMID,
MPFROMSHORT ( MI_ICON ) ,
0 ) ;
/* what is the extra space */
ulExtra = sizeof ( RECORDINFO ) -
sizeof ( MINIRECORDCORE ) ;
/* record info */
riRecord.cb = sizeof ( RECORDINSERT ) ;
riRecord.pRecordOrder = ( PRECORDCORE ) CMA_END ;
riRecord.fInvalidateRecord = FALSE ;
riRecord.zOrder = CMA_TOP ;
/* allocate the container memory for each record */
psiHeadRecord = ( PRECORDINFO ) PVOIDFROMMR (
WinSendMsg ( pcdData->hwndCnr,
CM_ALLOCRECORD,
MPFROMLONG ( ulExtra ) ,
MPFROMSHORT ( MAX_RECORDS ))) ;
/* set the current record at the first of the linked list */
psiRecords = psiHeadRecord ;
/* cycle through all records in memory, initializing */
/* each one */
for ( usIndex1 = 0 ; usIndex1 < MAX_RECORDS ;
usIndex1 ++ ) {
/* initialize */
initRecordInfo( pcdData, psiRecords, usIndex1 ) ;
/* get the next record in the linked list */
psiRecords =
(PRECORDINFO) psiRecords->mrcStd.preccNextRecord ;
} /* endfor */
/* records will have no parent, and number to be */
/* inserted is MAX_RECORDS */
riRecord.pRecordParent = NULL ;
riRecord.cRecordsInsert = MAX_RECORDS ;
/* insert all the records in one batch */
WinSendMsg ( pcdData->hwndCnr,
CM_INSERTRECORD,
MPFROMP ( psiHeadRecord ) ,
MPFROMP ( &riRecord )) ;
/* sort all the records */
WinSendMsg( pcdData->hwndCnr,
CM_SORTRECORD,
MPFROMP(pfnSortRecords),
MPVOID ) ;
WinSendMsg ( hwndClient,
WM_COMMAND,
MPFROMSHORT ( MI_ICON ) ,
0 ) ;
}
break ;
case WM_DESTROY:
freeCnrInfo ( pcdData->hwndCnr ) ;
if ( pcdData->hwndCnr ) {
WinDestroyWindow ( pcdData->hwndCnr ) ;
} /* endif */
if ( pcdData->hptrIcon ) {
WinDestroyPointer ( pcdData->hptrIcon ) ;
} /* endif */
free ( pcdData ) ;
break ;
case WM_SIZE:
if ( pcdData->hwndCnr != NULLHANDLE ) {
WinSetWindowPos ( pcdData->hwndCnr,
NULLHANDLE,
0,
0,
SHORT1FROMMP ( mpParm2 ) ,
SHORT2FROMMP ( mpParm2 ) ,
SWP_MOVE | SWP_SIZE ) ;
} /* endif */
break ;
/* once an item is chosen from the menu, turn off selection */
case WM_MENUEND:
switch ( SHORT1FROMMP ( mpParm1 )) {
case FID_MENU:
if ( pcdData->bCnrSelected ) {
WinSendMsg ( pcdData->hwndCnr,
CM_SETRECORDEMPHASIS,
0,
MPFROM2SHORT ( FALSE, CRA_SOURCE )) ;
pcdData->bCnrSelected = FALSE ;
} else {
emphasizeRecs ( pcdData->hwndCnr, FALSE ) ;
} /* endif */
break ;
default:
return WinDefWindowProc ( hwndClient,
ulMsg,
mpParm1,
mpParm2 ) ;
} /* endswitch */
break ;
case WM_CONTROL:
switch ( SHORT1FROMMP ( mpParm1 )) {
case WND_CONTAINER:
switch ( SHORT2FROMMP ( mpParm1 )) {
case CN_CONTEXTMENU:
{
PRECORDINFO psiRecord ;
POINTL ptlMouse ;
/* Get the record that the user selected for a menu */
psiRecord = ( PRECORDINFO ) PVOIDFROMMP ( mpParm2 ) ;
if ( psiRecord ) {
if (( psiRecord->mrcStd.flRecordAttr &
CRA_SELECTED ) == 0 )
{
/* if selected is FALSE, set it to SOURCE emphasis */
WinSendMsg ( pcdData->hwndCnr,
CM_SETRECORDEMPHASIS,
MPFROMP ( psiRecord ) ,
MPFROM2SHORT ( TRUE, CRA_SOURCE )) ;
psiRecord->bEmphasized = TRUE ;
} else {
/* find which records are selected and set */
/* SELECTED emphasis ON */
emphasizeRecs ( pcdData->hwndCnr, TRUE ) ;
} /* endif */
} else {
/* turn SOURCE emphasis on for the entire container */
WinSendMsg ( pcdData->hwndCnr,
CM_SETRECORDEMPHASIS,
0,
MPFROM2SHORT ( TRUE, CRA_SOURCE )) ;
pcdData->bCnrSelected = TRUE ;
} /* endif */
/* where is the pointer? */
WinQueryPointerPos ( HWND_DESKTOP, &ptlMouse ) ;
/* map the pointer to client window coordinates */
WinMapWindowPoints ( HWND_DESKTOP,
hwndClient,
&ptlMouse,
1 ) ;
/* popup menu */
WinPopupMenu ( hwndClient,
hwndClient,
pcdData->hwndMenu,
ptlMouse.x,
ptlMouse.y,
M_VIEWS,
PU_HCONSTRAIN |
PU_VCONSTRAIN |
PU_KEYBOARD |
PU_MOUSEBUTTON1 |
PU_MOUSEBUTTON2 |
PU_NONE ) ;
}
break ;
default:
return WinDefWindowProc ( hwndClient,
ulMsg,
mpParm1,
mpParm2 ) ;
} /* endswitch */
break ;
default:
return WinDefWindowProc ( hwndClient,
ulMsg,
mpParm1,
mpParm2 ) ;
} /* endswitch */
break ;
case WM_COMMAND:
switch ( SHORT1FROMMP ( mpParm1 )) {
case MI_ICON:
{
CNRINFO ciInfo ;
ciInfo.cb = sizeof ( CNRINFO ) ;
ciInfo.flWindowAttr = CV_ICON ;
WinSendMsg ( pcdData->hwndCnr,
CM_SETCNRINFO,
MPFROMP ( &ciInfo ) ,
MPFROMLONG ( CMA_FLWINDOWATTR )) ;
WinSendMsg ( pcdData->hwndCnr,
CM_ARRANGE,
NULL,
NULL ) ;
}
break ;
case MI_TREE:
{
CNRINFO ciInfo ;
ciInfo.cb = sizeof ( CNRINFO ) ;
ciInfo.flWindowAttr = CV_TREE | CV_ICON | CA_TREELINE ;
ciInfo.cxTreeIndent = - 1 ;
ciInfo.cxTreeLine = - 1 ;
WinSendMsg ( pcdData->hwndCnr,
CM_SETCNRINFO,
MPFROMP ( &ciInfo ) ,
MPFROMLONG ( CMA_FLWINDOWATTR )) ;
}
break ;
case MI_NAMEFLOWED:
{
CNRINFO ciInfo ;
ciInfo.cb = sizeof ( CNRINFO ) ;
ciInfo.flWindowAttr = CV_NAME | CV_FLOW ;
WinSendMsg ( pcdData->hwndCnr,
CM_SETCNRINFO,
MPFROMP ( &ciInfo ) ,
MPFROMLONG ( CMA_FLWINDOWATTR )) ;
WinSendMsg ( pcdData->hwndCnr,
CM_ARRANGE,
NULL,
NULL ) ;
}
break ;
case MI_TEXTFLOWED:
{
CNRINFO ciInfo ;
ciInfo.cb = sizeof ( CNRINFO ) ;
ciInfo.flWindowAttr = CV_TEXT | CV_FLOW ;
WinSendMsg ( pcdData->hwndCnr,
CM_SETCNRINFO,
MPFROMP ( &ciInfo ) ,
MPFROMLONG ( CMA_FLWINDOWATTR )) ;
WinSendMsg ( pcdData->hwndCnr,
CM_ARRANGE,
NULL,
NULL ) ;
}
break ;
case MI_EXIT:
WinPostMsg ( hwndClient, WM_CLOSE, 0, 0 ) ;
break ;
case MI_RESUME:
break ;
default:
return WinDefWindowProc ( hwndClient,
ulMsg,
mpParm1,
mpParm2 ) ;
} /* endswitch */
break ;
case WM_PAINT:
{
HPS hpsPaint ;
RECTL rclPaint ;
hpsPaint = WinBeginPaint ( hwndClient,
NULLHANDLE,
&rclPaint ) ;
WinFillRect ( hpsPaint, &rclPaint, SYSCLR_WINDOW ) ;
WinEndPaint ( hpsPaint ) ;
}
break ;
default:
return WinDefWindowProc ( hwndClient,
ulMsg,
mpParm1,
mpParm2 ) ;
} /* endswitch */
return MRFROMSHORT ( FALSE ) ;
}
/****************************************************************/
/* */
/* This routine is used to sort all records in the container */
/* */
/****************************************************************/
SHORT EXPENTRY pfnSortRecords( PMINIRECORDCORE pmr1,
PMINIRECORDCORE pmr2,
PVOID pStorage)
{
SHORT sBig ;
PRECORDINFO pRecord1, pRecord2 ;
pRecord1 = (PRECORDINFO)pmr1 ;
pRecord2 = (PRECORDINFO)pmr2 ;
sBig = strcmp( pRecord1->mrcStd.pszIcon, pRecord2->mrcStd.pszIcon ) ;
return (sBig ) ;
}
/****************************************************************/
/* */
/* This routine is used initialize all records in the container */
/* */
/****************************************************************/
VOID initRecordInfo ( PCLIENTDATA pcdData,
PRECORDINFO psiRecord,
USHORT usIndex )
{
psiRecord->mrcStd.cb = sizeof ( MINIRECORDCORE ) ;
psiRecord->mrcStd.pszIcon = malloc ( 256 ) ;
if ( psiRecord->mrcStd.pszIcon )
strcpy( psiRecord->mrcStd.pszIcon, pRecordTitles[usIndex] ) ;
psiRecord->mrcStd.hptrIcon = pcdData->hptrIcon ;
psiRecord->bEmphasized = FALSE ;
return ;
}
/****************************************************************/
/* */
/* This routine is used to turn on and off the emphasis for all */
/* selected records */
/* */
/****************************************************************/
VOID emphasizeRecs ( HWND hwndCnr, BOOL bEmphasize )
{
SHORT sFlag ;
PRECORDINFO psiRecord ;
/* Do I want source emphasis or selected emphasis */
sFlag = (( bEmphasize ) ? CRA_SELECTED : CRA_SOURCE ) ;
/* Get the first record with emphasis */
psiRecord = ( PRECORDINFO ) PVOIDFROMMR (
WinSendMsg ( hwndCnr,
CM_QUERYRECORDEMPHASIS,
MPFROMP ( CMA_FIRST ) ,
MPFROMSHORT ( sFlag )) ) ;
while ( psiRecord ) {
/* if TRUE, turn on SOURCE emphasis */
if ( bEmphasize ) {
WinSendMsg ( hwndCnr,
CM_SETRECORDEMPHASIS,
MPFROMP ( psiRecord ) ,
MPFROM2SHORT ( TRUE, CRA_SOURCE )) ;
psiRecord->bEmphasized = TRUE ;
} else {
/* if FALSE, turn off SOURCE emphasis */
WinSendMsg ( hwndCnr,
CM_SETRECORDEMPHASIS,
MPFROMP ( psiRecord ) ,
MPFROM2SHORT ( FALSE, CRA_SOURCE )) ;
psiRecord->bEmphasized = FALSE ;
} /* endif */
/* get next selected record */
psiRecord = ( PRECORDINFO ) PVOIDFROMMR (
WinSendMsg ( hwndCnr,
CM_QUERYRECORDEMPHASIS,
MPFROMP ( psiRecord ) ,
MPFROMSHORT ( sFlag ))) ;
} /* endwhile */
return ;
}
/****************************************************************/
/* */
/* this routine is called when the container is being close to */
/* free all the memory that was allocated for the container */
/* */
/****************************************************************/
VOID freeCnrInfo ( HWND hwndCnr )
{
PRECORDINFO psiRecord ;
/* get the first record */
psiRecord = ( PRECORDINFO ) PVOIDFROMMR (
WinSendMsg ( hwndCnr,
CM_QUERYRECORD,
0,
MPFROM2SHORT ( CMA_FIRST,
CMA_ITEMORDER ))) ;
while (psiRecord) {
/* free title string */
if ( psiRecord->mrcStd.pszIcon ) {
free ( psiRecord->mrcStd.pszIcon ) ;
} /* endif */
/* get next record */
psiRecord = ( PRECORDINFO ) PVOIDFROMMR (
WinSendMsg ( hwndCnr,
CM_QUERYRECORD,
MPFROMP ( psiRecord ) ,
MPFROM2SHORT ( CMA_NEXT,
CMA_ITEMORDER ))) ;
} /* endwhile */
return ;
}