Global variables used by the sample program
This section defines the global variables used by the sample program.
#include "stdafx.h"
#include <ddeml.h>
#include <winspool.h>
#include "vcdde32.h"
#include "MainDlg.h"
#include "arsddeex.h" // Shipped with Content Manager OnDemand
static CMainDlg * pMainDlg;
static char RequestedData[10000]; // Returned data from DDE command
static HSZ hsz1, hsz2;
DWORD DdeInstance;
HCONV hDdeConv;
extern CDdeTestApp * pApp; // Pointer to application instance
#define ERROR_MAP struct _ErrorMap
ERROR_MAP
{
int code;
char * pMsg;
};
static ERROR_MAP Errors[] =
{ { ARS_DDE_RC_UNKNOWN_COMMAND, "Unknown command." },
{ ARS_DDE_RC_PARM_NOT_SPECIFIED, "Parameter not specified." },
{ ARS_DDE_RC_INVALID_PARM_VALUE, "Invalid parameter value." },
{ ARS_DDE_RC_SERVER_ERROR, "Server error." },
{ ARS_DDE_RC_FILE_ERROR, "File error." },
{ ARS_DDE_RC_NOT_LOGGED_ON, "Not logged on." },
{ ARS_DDE_RC_MAX_FOLDERS_OPEN, "Maximum folders open." },
{ ARS_DDE_RC_FOLDER_NOT_OPEN, "Folder not open." },
{ ARS_DDE_RC_NO_DOC, "No document exists." },
{ ARS_DDE_RC_NO_ACTIVE_DOC, "No document is active." },
{ ARS_DDE_RC_USER_ACTION_IN_PROGRESS, "User action in process." },
{ ARS_DDE_RC_UNAUTHORIZED_OPERATION , "Unauthorized operation." },
{ ARS_DDE_RC_USER_CANCELLED_OPERATION, "User cancelled operation." },
{ ARS_DDE_RC_INVALID_APPL_GROUP_NAME, "Invalid Appl Group Name." },
{ ARS_DDE_RC_INVALID_APPL_NAME, "Invalid Appl Name." },
{ ARS_DDE_RC_INVALID_INTEGER_FIELD, "Invalid integer field." },
{ ARS_DDE_RC_INVALID_DECIMAL_FIELD, "Invalid decimal field." },
{ ARS_DDE_RC_INVALID_DATE_FIELD, "Invalid date field." },
{ ARS_DDE_RC_INVALID_APPLGRP_FIELD_TYPE, "Invalid Appl Group field type." } };
#define NUM_ERRORS ( sizeof(Errors) / sizeof(ERROR_MAP) )
#define ADV_MAP struct _AdvMap
ADV_MAP
{
char * pAdvData;
char * pMsg;
};
static ADV_MAP Advises[] =
{ { ARS_DDE_EVENT_CRITERIA_BUTTON_1, "DDE Criteria 1 Button Clicked." },
{ ARS_DDE_EVENT_CRITERIA_BUTTON_2, "DDE Criteria 2 Button Clicked." },
{ ARS_DDE_EVENT_CRITERIA_BUTTON_3, "DDE Criteria 3 Button Clicked." },
{ ARS_DDE_EVENT_CRITERIA_BUTTON_4, "DDE Criteria 4 Button Clicked." },
{ ARS_DDE_EVENT_CRITERIA_BUTTON_5, "DDE Criteria 5 Button Clicked." },
{ ARS_DDE_EVENT_DOCLIST_BUTTON_1, "DDE Doclist 1 Button Clicked." },
{ ARS_DDE_EVENT_DOCLIST_BUTTON_2, "DDE Doclist 2 Button Clicked." },
{ ARS_DDE_EVENT_DOCLIST_BUTTON_3, "DDE Doclist 3 Button Clicked." },
{ ARS_DDE_EVENT_DOCLIST_BUTTON_4, "DDE Doclist 4 Button Clicked." },
{ ARS_DDE_EVENT_DOCLIST_BUTTON_5, "DDE Doclist 5 Button Clicked." },
{ ARS_DDE_EVENT_SWITCH_FOCUS, "Switch focus requested." },
{ ARS_DDE_EVENT_SWITCH_FOCUS_2, "Switch focus *** 2 *** requested." },
{ ARS_DDE_EVENT_SWITCH_FOCUS_3, "Switch focus *** 3 *** requested." },
{ ARS_DDE_EVENT_SWITCH_FOCUS_4, "Switch focus *** 4 *** requested." },
{ ARS_DDE_EVENT_SWITCH_FOCUS_5, "Switch focus *** 5 *** requested." } };
#define NUM_ADVISES ( sizeof(Advises) / sizeof(ADV_MAP) )
// DDE variables and functions
static HDDEDATA hDdeData, hDdeResult;
HDDEDATA FAR PASCAL DdeCallBack ( UINT iType,
UINT iFmt,
HCONV hConv,
HSZ hsz1,
HSZ hsz2,
HDDEDATA hData,
DWORD dwData1,
DWORD dwData2 )
{
int j;
char * pData;
DWORD data_len;
switch ( iType )
{
case XTYP_DISCONNECT:
hDdeConv = NULL;
break;
case XTYP_ADVDATA:
if ( hData == NULL )
AfxMessageBox( "hData is NULL in XTYP_ADVDATA" );
else
{
pData = (char*)DdeAccessData( hData, &data_len );
for ( j = 0; j < NUM_ADVISES; j++ )
if ( strcmp( Advises[j].pAdvData, pData ) == 0 )
break;
AfxMessageBox( j < NUM_ADVISES
? Advises[j].pMsg
: "Logic Error - invalid ADVDATA." );
DdeUnaccessData( hData );
}
break;
}
return NULL;
}
static BOOL DoDdeCommand( char * pCommand, char * pParms )
{
DWORD data_len;
char * pString1, * pData, * pFirstChar;
int j, rc;
if ( pParms == NULL )
pParms = "";
pString1 = new char[ strlen( pCommand ) + strlen( pParms ) + 2 ];
strcpy( pString1, pCommand );
strcat( pString1, " " );
strcat( pString1, pParms );
hsz1 = DdeCreateStringHandle( DdeInstance, pString1, 0 );
hDdeResult = DdeClientTransaction( NULL,
0,
hDdeConv,
hsz1,
CF_TEXT,
XTYP_REQUEST,
120000L,
NULL );
DdeFreeStringHandle( DdeInstance, hsz1 );
delete pString1;
RequestedData[0] = '\0';
if ( hDdeResult == NULL )
{
int error;
char * pErr;
error = DdeGetLastError( DdeInstance );
switch ( error )
{
case DMLERR_ADVACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_ADVACKTIMEOUT";
break;
case DMLERR_BUSY:
pErr = "DdeClientTransaction failed with DMLERR_BUSY";
break;
case DMLERR_DATAACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_DATAACKTIMEOUT";
break;
case DMLERR_DLL_NOT_INITIALIZED:
pErr = "DdeClientTransaction failed with DMLERR_DLL_NOT_INITIALIZED";
break;
case DMLERR_DLL_USAGE:
pErr = "DdeClientTransaction failed with DMLERR_DLL_USAGE";
break;
case DMLERR_EXECACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_EXECACKTIMEOUT";
break;
case DMLERR_INVALIDPARAMETER:
pErr = "DdeClientTransaction failed with DMLERR_INVALIDPARAMETER";
break;
case DMLERR_LOW_MEMORY:
pErr = "DdeClientTransaction failed with DMLERR_LOW_MEMORY";
break;
case DMLERR_MEMORY_ERROR:
pErr = "DdeClientTransaction failed with DMLERR_MEMORY_ERROR";
break;
case DMLERR_NO_CONV_ESTABLISHED:
pErr = "DdeClientTransaction failed with DMLERR_NO_CONV_ESTABLISHED";
break;
case DMLERR_NOTPROCESSED:
pErr = "DdeClientTransaction failed with DMLERR_NOTPROCESSED";
break;
case DMLERR_POKEACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_POKEACKTIMEOUT";
break;
case DMLERR_POSTMSG_FAILED:
pErr = "DdeClientTransaction failed with DMLERR_POSTMSG_FAILED";
break;
case DMLERR_REENTRANCY:
pErr = "DdeClientTransaction failed with DMLERR_REENTRANCY";
break;
case DMLERR_SERVER_DIED:
pErr = "DdeClientTransaction failed with DMLERR_SERVER_DIED";
break;
case DMLERR_SYS_ERROR:
pErr = "DdeClientTransaction failed with DMLERR_SYS_ERROR";
break;
case DMLERR_UNADVACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_UNADVACKTIMEOUT";
break;
case DMLERR_UNFOUND_QUEUE_ID:
pErr = "DdeClientTransaction failed with DMLERR_UNFOUND_QUEUE_ID";
break;
}
AfxMessageBox( pErr );
return FALSE;
}
else
{
pData = (char*)DdeAccessData( hDdeResult, &data_len );
rc = atoi( pData );
if ( rc == ARS_DDE_RC_NO_ERROR )
{
pFirstChar = strchr( pData, ' ' );
strcpy( RequestedData, &pFirstChar[1] );
}
else
{
for ( j = 0; j < NUM_ERRORS; j++ )
if ( Errors[j].code == rc )
break;
AfxMessageBox( j < NUM_ERRORS
? Errors[j].pMsg
: "Logic Error - invalid return code." );
}
DdeUnaccessData( hDdeResult );
return rc == ARS_DDE_RC_NO_ERROR;
}
}
static BOOL DoAdviseLoop( char * pName, BOOL stop )
{
hsz1 = DdeCreateStringHandle( DdeInstance, pName, 0 );
hDdeResult = DdeClientTransaction( NULL,
0,
hDdeConv,
hsz1,
CF_TEXT,
stop ? XTYP_ADVSTOP : XTYP_ADVSTART,
120000L,
NULL );
DdeFreeStringHandle( DdeInstance, hsz1 );
if ( hDdeResult == NULL )
{
int error;
char * pErr;
error = DdeGetLastError( DdeInstance );
switch ( error )
{
case DMLERR_ADVACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_ADVACKTIMEOUT";
break;
case DMLERR_BUSY:
pErr = "DdeClientTransaction failed with DMLERR_BUSY";
break;
case DMLERR_DATAACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_DATAACKTIMEOUT";
break;
case DMLERR_DLL_NOT_INITIALIZED:
pErr = "DdeClientTransaction failed with DMLERR_DLL_NOT_INITIALIZED";
break;
case DMLERR_DLL_USAGE:
pErr = "DdeClientTransaction failed with DMLERR_DLL_USAGE";
break;
case DMLERR_EXECACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_EXECACKTIMEOUT";
break;
case DMLERR_INVALIDPARAMETER:
pErr = "DdeClientTransaction failed with DMLERR_INVALIDPARAMETER";
break;
case DMLERR_LOW_MEMORY:
pErr = "DdeClientTransaction failed with DMLERR_LOW_MEMORY";
break;
case DMLERR_MEMORY_ERROR:
pErr = "DdeClientTransaction failed with DMLERR_MEMORY_ERROR";
break;
case DMLERR_NO_CONV_ESTABLISHED:
pErr = "DdeClientTransaction failed with DMLERR_NO_CONV_ESTABLISHED";
break;
case DMLERR_NOTPROCESSED:
pErr = "DdeClientTransaction failed with DMLERR_NOTPROCESSED";
break;
case DMLERR_POKEACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_POKEACKTIMEOUT";
break;
case DMLERR_POSTMSG_FAILED:
pErr = "DdeClientTransaction failed with DMLERR_POSTMSG_FAILED";
break;
case DMLERR_REENTRANCY:
pErr = "DdeClientTransaction failed with DMLERR_REENTRANCY";
break;
case DMLERR_SERVER_DIED:
pErr = "DdeClientTransaction failed with DMLERR_SERVER_DIED";
break;
case DMLERR_SYS_ERROR:
pErr = "DdeClientTransaction failed with DMLERR_SYS_ERROR";
break;
case DMLERR_UNADVACKTIMEOUT:
pErr = "DdeClientTransaction failed with DMLERR_UNADVACKTIMEOUT";
break;
case DMLERR_UNFOUND_QUEUE_ID:
pErr = "DdeClientTransaction failed with DMLERR_UNFOUND_QUEUE_ID";
break;
}
AfxMessageBox( pErr );
return FALSE;
}
else
return TRUE;
}
/////////////////////////////////////////////////////////////////////////////
// CMainDlg dialog
CMainDlg::CMainDlg(CWnd* pParent /*=NULL*/)
: CDialog(CMainDlg::IDD, pParent)
{
//{{AFX_DATA_INIT(CMainDlg)
// NOTE: the ClassWizard will add member initialization here
//}}AFX_DATA_INIT
// Note that LoadIcon does not require a subsequent DestroyIcon in Win32
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}
void CMainDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CMainDlg)
// NOTE: the ClassWizard will add DDX and DDV calls here
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CMainDlg, CDialog)
//{{AFX_MSG_MAP(CMainDlg)
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_LBN_DBLCLK(IDC_DOCLIST, OnDblclkDoclist)
ON_BN_CLICKED(IDC_PRINT, OnPrint)
ON_BN_CLICKED(IDC_CLOSE, OnCloseDlg)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CMainDlg message handlers
BOOL CMainDlg::OnInitDialog()
{
CListBox * pList = (CListBox*)GetDlgItem( IDC_DOCLIST );
CComboBox * pPrinterList = (CComboBox*)GetDlgItem( IDC_PRINTERS );
long l, num_hits;
char * pToken;
PROCESS_INFORMATION pi;
STARTUPINFO &sui;
char cmd[300], Misc[100];
BOOL rc;
DWORD id;
CDialog::OnInitDialog();
pMainDlg = this;
DdeInstance = 0;
m_DocOpened = FALSE;
m_DocID = 0;
( (CButton*)GetDlgItem( IDC_PRINT ) )->EnableWindow( FALSE );
SetIcon(m_hIcon, FALSE);
// Start up the Content Manager OnDemand client
// /I - Enable DDE Interface
// /W - Window placement (N = hidden)
// /V - Disable anticipation
// /B - Disable User Confirmation
strcpy( cmd, "g:\\ars32\\arsgui.exe /I /W N /V /B /1 g:\\ars32\\locale\\enu" );
memset( &sui, 0, sizeof(STARTUPINFO) );
sui.cb = sizeof(STARTUPINFO);
rc = CreateProcess( NULL, cmd, NULL, NULL, FALSE, CREATE_NEW_CONSOLE, NULL, NULL, &sui, &pi );
if ( !rc )
{
id = GetLastError( );
FormatMessage( FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
NULL, id, 0, cmd, sizeof(cmd), NULL );
sprintf( Misc, "CreateProcessFailed - %s", cmd );
AfxMessageBox( Misc );
Misc[0] = '\0';
}
else
{
// Start a dde conversation with the client.
if ( DdeInstance == 0 )
{
FARPROC pfnDdeCallBack;
pfnDdeCallBack = MakeProcInstance( (FARPROC)DdeCallBack, pApp->m_hInstance );
DdeInitialize( &DdeInstance,
(PFNCALLBACK)pfnDdeCallBack,
APPCLASS_STANDARD | APPCMD_CLIENTONLY,
0L );
}
hsz1 = DdeCreateStringHandle( DdeInstance, ARS_DDE_SERVICE, 0 );
hsz2 = DdeCreateStringHandle( DdeInstance, ARS_DDE_TOPIC, 0 );
for ( int j = 0; j < 1000; j++ )
{
hDdeConv = DdeConnect( DdeInstance, hsz1, hsz2, NULL );
if ( hDdeConv != NULL )
break;
}
DdeFreeStringHandle( DdeInstance, hsz1 );
DdeFreeStringHandle( DdeInstance, hsz2 );
if ( hDdeConv == NULL )
AfxMessageBox( "Unable to connect to ARSGUI." );
else
{
int k;
// Begin sending dde commands to the client.
Misc[0] = '/';
Misc[1] = ARS_DDE_SWITCH_HANDLE;
sprintf( &Misc[2], "%ld", (long)(char far *)pApp->m_pMainWnd->m_hWnd );
strcat( Misc, " " );
strcat( Misc, " /" );
k = strlen( Misc );
Misc[k++] = ARS_DDE_SWITCH_CLIENT_NAME;
strcpy( &Misc[k], "DDE Partner 1" );
DoDdeCommand( ARS_DDE_CMD_ENABLE_SWITCH_FOCUS, Misc );
DoDdeCommand( ARS_DDE_CMD_LOGON, "/S gunnar /U demo /P" );
DoDdeCommand( ARS_DDE_CMD_OPEN_FOLDER, "/F Credit Card Statementss" );
DoDdeCommand( ARS_DDE_CMD_SEARCH_FOLDER, "" );
if ( DoDdeCommand( ARS_DDE_CMD_GET_NUM_DOCS_IN_LIST, "" ) )
{
num_hits = atol( RequestedData );
for ( l = 0; l < num_hits; l++ )
{
Misc[0] = '/';
Misc[1] = ARS_DDE_DOC_NUMBER;
sprintf( &Misc[2], "%ld", l );
if ( DoDdeCommand( ARS_DDE_CMD_GET_DOC_VALUES, Misc ) )
{
for ( pToken = strtok( RequestedData, ARS_DDE_DATA_SEPARATOR ),
Misc[0] = '\0';
pToken != NULL;
pToken = strtok( NULL, ARS_DDE_DATA_SEPARATOR ) )
{
strcat( Misc, pToken );
strcat( Misc, " - " );
}
if ( Misc[0] != '\0' )
{
j = pList->InsertString( -1, Misc );
pList->SetItemData( j, (DWORD)l );
}
}
else
break;
}
}
DoAdviseLoop( ARS_DDE_ADVISE_LOOP_1, FALSE );
}
}
if ( DoDdeCommand( ARS_DDE_CMD_GET_PRINTERS, "/L" ) )
{
for ( pToken = strtok( RequestedData, ARS_DDE_DATA_SEPARATOR );
pToken != NULL;
pToken = strtok( NULL, ARS_DDE_DATA_SEPARATOR ) )
pPrinterList->InsertString( -1, pToken );
pPrinterList->SetCurSel( 0 );
}
return TRUE;
}
void CMainDlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // device context for painting
SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);
// Center icon in client rectangle
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// Draw the icon
dc.DrawIcon(x, y, m_hIcon);
}
else
{
CDialog::OnPaint();
}
}
// The system calls this to obtain the cursor to display while the user drags
// the minimized window.
HCURSOR CMainDlg::OnQueryDragIcon()
{
return (HCURSOR) m_hIcon;
}
void CMainDlg::OnDblclkDoclist()
{
CListBox * pDocsList;
char printer[100];
char Misc[100];
pDocsList = (CListBox*)GetDlgItem( IDC_DOCLIST );
if( m_DocOpened )
{
sprintf( Misc, "/D %d", m_DocID );
DoDdeCommand( ARS_DDE_CMD_CLOSE_DOC, Misc );
}
Misc[0] = '/';
Misc[1] = ARS_DDE_DOC_NUMBER;
sprintf( &Misc[2], "%d", (int)pDocsList->GetCurSel() );
if ( DoDdeCommand( ARS_DDE_CMD_OPEN_DOC, Misc ) )
{
m_DocID = atol( RequestedData );
m_DocOpened = TRUE;
DoDdeCommand( ARS_DDE_CMD_SHOW_WINDOW, "/W" );
}
else
{
m_DocID = 0;
m_DocOpened = TRUE;
}
GetDlgItem( IDC_PRINTERS )->GetWindowText( printer, sizeof(printer) );
if( printer != NULL && printer[0] != '\0' )
( (CButton*)GetDlgItem( IDC_PRINT ) )->EnableWindow( TRUE );
}
void CMainDlg::OnPrint()
{
char printer[100];
char Misc[100];
GetDlgItem( IDC_PRINTERS )->GetWindowText( printer, sizeof(printer) );
Misc[0] = '\0';
sprintf( Misc, "/L %s", printer );
DoDdeCommand( ARS_DDE_CMD_PRINT_DOC, Misc );
}
void CMainDlg::OnCloseDlg()
{
char Misc[100];
if( m_DocOpened )
{
sprintf( Misc, "/D %d", m_DocID );
DoDdeCommand( ARS_DDE_CMD_CLOSE_DOC, Misc );
}
DoDdeCommand( ARS_DDE_CMD_CLOSE_FOLDER, "" );
DoDdeCommand( ARS_DDE_CMD_LOGOFF, "" );
DoDdeCommand( ARS_DDE_CMD_EXIT, "" );
EndDialog(0);
}