Developing A Simple MTS Client
using Visual
C++
Gopalan Suresh Raj
Note |
To
work with any of these samples, you will need the
following: .........................................Microsoft Visual C++ ver 6.0 .........................................Windows NT 4.0 Options Pack |
The ClickClient counts and displays the number of times the User clicks on the "Click Here..." button during the lifetime of this client app. It uses the ClickServer to increment the count (Looks like our ClickClient client program is mathematically challenged :-) !!!!!!!!).
Figure : Shows the
ClickClient MTS client program in action
The Steps involved in developing the MTS Client are
1. Create a new Dialog based Windows Application
2. Add code in the Client to call the MTS Server
3. Build and Run the Client
1. Create a new
Windows Application
Create a Dialog Based Windows
Application project in Visual C++ by selecting the New Project in
the File menu, then choosing the MFC AppWizard (EXE) project
template. Name the project ClickClient and choose Open.
2. Add code in the
ClickClient to call the ClickServer MTS component
This is where we add code to
the Client apps form to interact with the MTS ClickServer
component.
1) Create a Dialog form similar to the one shown below.
Figure : Shows the form that
we need to develop for our ClickClient program
2) To the "StdAfx.h" file, add the following piece of code:
#import "E:\com\gopalan\ClickServer\ClickServer.tlb" no_namespace
3) To the "ClickClient.cpp" file, add this piece of code in the InitInstance() of the Application just before the dialog is created:
// Init OLE libraries and support if ( !AfxOleInit() ) { AfxMessageBox ("OLE Initialization failed"); return FALSE; }
4) To the CClientDialog class in the file "ClickClientDlg.h", add a couple of members:
IServerPtr m_pServer; // pointer to the MTS Server Component reference int m_nClickCount // maintains the number of times client called server;
5) To the CClickClientDlg::OnInitDialog() member implementation in the file "ClickClientDlg.cpp", add the following code:
CLSID clsid; HRESULT hResult; hResult = CLSIDFromProgID (OLESTR("ClickServer.Server"), &clsid); if (FAILED(hResult)) { AfxMessageBox ("Retrieval of ProgID failed..."); return FALSE; } m_pServer.CreateInstance (clsid);
6) Add code to the CClickClientDlg::OnClickHere() method in the file "ClickClientDlg.cpp", so that the MTS Server component is invoked from the client whenever the "Click Here..." button is pressed on the dialog form.
void CClickClientDlg::OnClickHere() { // TODO: Add your control notification handler code here CStatic* pStatic = (CStatic*) GetDlgItem (IDC_STATIC); CString str; try { m_pServer->Increment (&m_nClickCount); } catch (...) { } str.Format ("That was Click Number %d, Buddy...", m_nClickCount); pStatic->SetWindowText(str); }
The completed code for StdAfx.h is shown below:
StdAfx.h |
// stdafx.h : include file for standard system include files, // or project specific include files that are used frequently, but // are changed infrequently // #if !defined(AFX_STDAFX_H__928D10D9_876E_11D3_9822_006097A7D34F__INCLUDED_) #define AFX_STDAFX_H__928D10D9_876E_11D3_9822_006097A7D34F__INCLUDED_ #if _MSC_VER > 1000 #pragma once #endif // _MSC_VER > 1000 #define VC_EXTRALEAN // Exclude rarely-used stuff from Windows headers #include <afxwin.h> // MFC core and standard components #include <afxext.h> // MFC extensions #include <afxdisp.h> // MFC Automation classes #include <afxdtctl.h> // MFC support for Internet Explorer 4 Common Controls #ifndef _AFX_NO_AFXCMN_SUPPORT #include <afxcmn.h> // MFC support for Windows Common Controls #endif // _AFX_NO_AFXCMN_SUPPORT #import "E:\com\gopalan\ClickServer\ClickServer.tlb" no_namespace //{{AFX_INSERT_LOCATION}} // Microsoft Visual C++ will insert additional declarations immediately before the previous line. #endif // !defined(AFX_STDAFX_H__928D10D9_876E_11D3_9822_006097A7D34F__INCLUDED_) |
The completed code for ClickClient.cpp is shown below:
ClickClient.cpp |
// ClickClient.cpp : Defines the class behaviors for the application. // #include "stdafx.h" #include "ClickClient.h" #include "ClickClientDlg.h" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif ///////////////////////////////////////////////////////////////////////////// // CClickClientApp BEGIN_MESSAGE_MAP(CClickClientApp, CWinApp) //{{AFX_MSG_MAP(CClickClientApp) // NOTE - the ClassWizard will add and remove mapping macros here. // DO NOT EDIT what you see in these blocks of generated code! //}}AFX_MSG ON_COMMAND(ID_HELP, CWinApp::OnHelp) END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CClickClientApp construction CClickClientApp::CClickClientApp() { // TODO: add construction code here, // Place all significant initialization in InitInstance } ///////////////////////////////////////////////////////////////////////////// // The one and only CClickClientApp object CClickClientApp theApp; ///////////////////////////////////////////////////////////////////////////// // CClickClientApp initialization BOOL CClickClientApp::InitInstance() { AfxEnableControlContainer(); // Standard initialization // If you are not using these features and wish to reduce the size // of your final executable, you should remove from the following // the specific initialization routines you do not need. #ifdef _AFXDLL Enable3dControls(); // Call this when using MFC in a shared DLL #else Enable3dControlsStatic(); // Call this when linking to MFC statically #endif // Init OLE libraries and support if ( !AfxOleInit() ) { AfxMessageBox ("OLE Initialization failed"); return FALSE; } CClickClientDlg dlg; m_pMainWnd = &dlg; int nResponse = dlg.DoModal(); if (nResponse == IDOK) { // TODO: Place code here to handle when the dialog is // dismissed with OK } else if (nResponse == IDCANCEL) { // TODO: Place code here to handle when the dialog is // dismissed with Cancel } // Since the dialog has been closed, return FALSE so that we exit the // application, rather than start the application's message pump. return FALSE; } |
The completed code for ClickClientDlg.h is shown below:
ClickClientDlg.h |
// ClickClientDlg.h : header file // #if !defined(AFX_CLICKCLIENTDLG_H__928D10D7_876E_11D3_9822_006097A7D34F__INCLUDED_) #define AFX_CLICKCLIENTDLG_H__928D10D7_876E_11D3_9822_006097A7D34F__INCLUDED_ #if _MSC_VER > 1000 #pragma once #endif // _MSC_VER > 1000 ///////////////////////////////////////////////////////////////////////////// // CClickClientDlg dialog class CClickClientDlg : public CDialog { // Construction public: CClickClientDlg(CWnd* pParent = NULL); // standard constructor // Dialog Data //{{AFX_DATA(CClickClientDlg) enum { IDD = IDD_CLICKCLIENT_DIALOG }; // NOTE: the ClassWizard will add data members here //}}AFX_DATA // ClassWizard generated virtual function overrides //{{AFX_VIRTUAL(CClickClientDlg) protected: virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support //}}AFX_VIRTUAL // Implementation protected: HICON m_hIcon; // Generated message map functions //{{AFX_MSG(CClickClientDlg) virtual BOOL OnInitDialog(); afx_msg void OnSysCommand(UINT nID, LPARAM lParam); afx_msg void OnPaint(); afx_msg HCURSOR OnQueryDragIcon(); afx_msg void OnClickHere(); //}}AFX_MSG DECLARE_MESSAGE_MAP() private: IServerPtr m_pServer; // pointer to the MTS Server Component reference int m_nClickCount;// maintains the number of times client called server; }; //{{AFX_INSERT_LOCATION}} // Microsoft Visual C++ will insert additional declarations immediately before the previous line. #endif // !defined(AFX_CLICKCLIENTDLG_H__928D10D7_876E_11D3_9822_006097A7D34F__INCLUDED_) |
The completed code for ClickClientDlg.cpp is shown below:
ClickClientDlg.cpp |
// ClickClientDlg.cpp : implementation file // #include "stdafx.h" #include "ClickClient.h" #include "ClickClientDlg.h" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif ///////////////////////////////////////////////////////////////////////////// // CAboutDlg dialog used for App About class CAboutDlg : public CDialog { public: CAboutDlg(); // Dialog Data //{{AFX_DATA(CAboutDlg) enum { IDD = IDD_ABOUTBOX }; //}}AFX_DATA // ClassWizard generated virtual function overrides //{{AFX_VIRTUAL(CAboutDlg) protected: virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support //}}AFX_VIRTUAL // Implementation protected: //{{AFX_MSG(CAboutDlg) //}}AFX_MSG DECLARE_MESSAGE_MAP() }; CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD) { //{{AFX_DATA_INIT(CAboutDlg) //}}AFX_DATA_INIT } void CAboutDlg::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(CAboutDlg) //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CAboutDlg, CDialog) //{{AFX_MSG_MAP(CAboutDlg) // No message handlers //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CClickClientDlg dialog CClickClientDlg::CClickClientDlg(CWnd* pParent /*=NULL*/) : CDialog(CClickClientDlg::IDD, pParent) { //{{AFX_DATA_INIT(CClickClientDlg) // 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); m_nClickCount = 0; } void CClickClientDlg::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(CClickClientDlg) // NOTE: the ClassWizard will add DDX and DDV calls here //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CClickClientDlg, CDialog) //{{AFX_MSG_MAP(CClickClientDlg) ON_WM_SYSCOMMAND() ON_WM_PAINT() ON_WM_QUERYDRAGICON() ON_BN_CLICKED(ID_CLICKHERE, OnClickHere) //}}AFX_MSG_MAP END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CClickClientDlg message handlers BOOL CClickClientDlg::OnInitDialog() { CDialog::OnInitDialog(); // Add "About..." menu item to system menu. // IDM_ABOUTBOX must be in the system command range. ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX); ASSERT(IDM_ABOUTBOX < 0xF000); CMenu* pSysMenu = GetSystemMenu(FALSE); if (pSysMenu != NULL) { CString strAboutMenu; strAboutMenu.LoadString(IDS_ABOUTBOX); if (!strAboutMenu.IsEmpty()) { pSysMenu->AppendMenu(MF_SEPARATOR); pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu); } } // Set the icon for this dialog. The framework does this automatically // when the application's main window is not a dialog SetIcon(m_hIcon, TRUE); // Set big icon SetIcon(m_hIcon, FALSE); // Set small icon // TODO: Add extra initialization here CLSID clsid; HRESULT hResult; hResult = CLSIDFromProgID (OLESTR("ClickServer.Server"), &clsid); if (FAILED(hResult)) { AfxMessageBox ("Retrieval of ProgID failed..."); return FALSE; } m_pServer.CreateInstance (clsid); return TRUE; // return TRUE unless you set the focus to a control } void CClickClientDlg::OnSysCommand(UINT nID, LPARAM lParam) { if ((nID & 0xFFF0) == IDM_ABOUTBOX) { CAboutDlg dlgAbout; dlgAbout.DoModal(); } else { CDialog::OnSysCommand(nID, lParam); } } // If you add a minimize button to your dialog, you will need the code below // to draw the icon. For MFC applications using the document/view model, // this is automatically done for you by the framework. void CClickClientDlg::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 CClickClientDlg::OnQueryDragIcon() { return (HCURSOR) m_hIcon; } void CClickClientDlg::OnClickHere() { // TODO: Add your control notification handler code here CStatic* pStatic = (CStatic*) GetDlgItem (IDC_STATIC); CString str; try { m_pServer->Increment (&m_nClickCount); } catch (...) { } str.Format ("That was Click Number %d, Buddy...", m_nClickCount); pStatic->SetWindowText(str); } |
4. Build and Run the Client
program - ClickClient
Build the project by
selecting Build from the Build menu. This creates a Windows
executable with all the class files needed to execute the client.
Run it and have fun...
Download the Entire Source as a Zip file
click here to go to the Developing a Simple MTS Server Component Page... |
click here to go to My MTS HomePage... |
This site was developed and is maintained by Gopalan Suresh Raj This page has been visited times since February 24,1999. |
Last Updated : Feb 24, '99 |
Copyright (c) 1997-99, Gopalan Suresh Raj - All rights reserved. Terms of use. |
All products and companies mentioned at this site,are trademarks of their respective owners. |