|
|
//**********************************************************************
// File name: app.cpp
//
// Implementation file for the CSimpleApp Class
//
// Functions:
//
// See app.h for a list of member functions.
//
// Copyright (c) 1992 - 1993 Microsoft Corporation. All rights reserved.
//**********************************************************************
#include "pre.h"
#include "iocs.h"
#include "ias.h"
#include "app.h"
#include "site.h"
#include "doc.h"
#include <testmess.h>
#ifdef WIN32
extern INT_PTR CALLBACK About(HWND hDlg,UINT message,WPARAM wParam,LPARAM lParam); #endif
//**********************************************************************
//
// CSimpleApp::CSimpleApp()
//
// Purpose:
//
// Constructor for CSimpleApp
//
// Parameters:
//
// None
//
// Return Value:
//
// None
//
// Function Calls:
// Function Location
//
// TestDebugOut Windows API
//
//********************************************************************
CSimpleApp::CSimpleApp() { TestDebugOut("In CSimpleApp's Constructor \r\n");
// Set Ref Count
m_nCount = 0;
// clear members
m_hAppWnd = NULL; m_hInst = NULL; m_lpDoc = NULL;
// clear flags
m_fInitialized = FALSE;
// Initialize effects we allow.
m_dwSourceEffect = DROPEFFECT_COPY | DROPEFFECT_MOVE; m_dwTargetEffect = DROPEFFECT_COPY | DROPEFFECT_MOVE; }
//**********************************************************************
//
// CSimpleApp::~CSimpleApp()
//
// Purpose:
//
// Destructor for CSimpleApp Class.
//
// Parameters:
//
// None
//
// Return Value:
//
// None
//
// Function Calls:
// Function Location
//
// OutdebugString Windows API
// OleUninitialize OLE API
//
//
//********************************************************************
CSimpleApp::~CSimpleApp() { TestDebugOut("In CSimpleApp's Destructor\r\n");
// need to uninit the library...
if (m_fInitialized) OleUninitialize(); }
//**********************************************************************
//
// CSimpleApp::DestroyDocs()
//
// Purpose:
//
// Destroys all of the open documents in the application (Only one
// since this is an SDI app, but could easily be modified to
// support MDI).
//
// Parameters:
//
// None
//
// Return Value:
//
// None
//
// Function Calls:
// Function Location
//
// CSimpleDoc::Close DOC.CPP
//
//********************************************************************
void CSimpleApp::DestroyDocs() { m_lpDoc->Close(); // we have only 1 document
}
//**********************************************************************
//
// CSimpleApp::QueryInterface
//
// Purpose:
//
// Used for interface negotiation at the Application level.
//
// Parameters:
//
// REFIID riid - A reference to the interface that is
// being queried.
//
// LPVOID FAR* ppvObj - An out parameter to return a pointer to
// the interface.
//
// Return Value:
//
// S_OK - The interface is supported.
// S_FALSE - The interface is not supported
//
// Function Calls:
// Function Location
//
// TestDebugOut Windows API
// ResultFromScode OLE API
//
//********************************************************************
STDMETHODIMP CSimpleApp::QueryInterface(REFIID riid, LPVOID FAR* ppvObj) { TestDebugOut("In CSimpleApp::QueryInterface\r\n");
*ppvObj = NULL; // must set out pointer parameters to NULL
// Not a supported interface
return ResultFromScode(E_NOINTERFACE); }
//**********************************************************************
//
// CSimpleApp::AddRef
//
// Purpose:
//
// Adds to the reference count at the Application level.
//
// Parameters:
//
// None
//
// Return Value:
//
// ULONG - The new reference count of the application.
//
// Function Calls:
// Function Location
//
// TestDebugOut Windows API
//
// Comments:
//
// Due to the reference counting model that is used in this
// implementation, this reference count is the sum of the
// reference counts on all interfaces of all objects open
// in the application.
//
//********************************************************************
STDMETHODIMP_(ULONG) CSimpleApp::AddRef() { TestDebugOut("In CSimpleApp::AddRef\r\n"); return ++m_nCount; }
//**********************************************************************
//
// CSimpleApp::Release
//
// Purpose:
//
// Decrements the reference count at the application level
//
// Parameters:
//
// None
//
// Return Value:
//
// ULONG - The new reference count of the application.
//
// Function Calls:
// Function Location
//
// TestDebugOut Windows API
//
//
//********************************************************************
STDMETHODIMP_(ULONG) CSimpleApp::Release() { TestDebugOut("In CSimpleApp::Release\r\n");
if (--m_nCount == 0) { delete this; return 0; } return m_nCount; }
//**********************************************************************
//
// CSimpleApp::fInitApplication
//
// Purpose:
//
// Initializes the application
//
// Parameters:
//
// HANDLE hInstance - Instance handle of the application.
//
// Return Value:
//
// TRUE - Application was successfully initialized.
// FALSE - Application could not be initialized
//
// Function Calls:
// Function Location
//
// LoadIcon Windows API
// LoadCursor Windows API
// GetStockObject Windows API
// RegisterClass Windows API
//
//
//********************************************************************
BOOL CSimpleApp::fInitApplication(HANDLE hInstance) { WNDCLASS wc;
// Fill in window class structure with parameters that describe the
// main window.
wc.style = NULL; // Class style(s).
wc.lpfnWndProc = MainWndProc; // Function to retrieve messages for
// windows of this class.
wc.cbClsExtra = 0; // No per-class extra data.
wc.cbWndExtra = 0; // No per-window extra data.
wc.hInstance =(HINSTANCE) hInstance; // Application that owns
// the class.
wc.hIcon = LoadIcon((HINSTANCE)hInstance,TEXT("SimpDnd")); wc.hCursor = LoadCursor(NULL, IDC_ARROW); wc.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH); wc.lpszMenuName = TEXT("SIMPLEMENU"); // Name of menu resource in
// .RC file.
wc.lpszClassName = TEXT("SimpDndAppWClass"); // Name used in
// CreateWindow call.
if (!RegisterClass(&wc)) return FALSE;
wc.style = CS_DBLCLKS; // Class style(s). allow DBLCLK's
wc.lpfnWndProc = DocWndProc; // Function to retrieve messages for
// windows of this class.
wc.cbClsExtra = 0; // No per-class extra data.
wc.cbWndExtra = 0; // No per-window extra data.
wc.hInstance = (HINSTANCE) hInstance; // Application that owns
// the class.
wc.hIcon = NULL; wc.hCursor = LoadCursor(NULL, IDC_ARROW); wc.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH); wc.lpszMenuName = NULL; wc.lpszClassName = TEXT("SimpDndDocWClass"); // Name used in
//CreateWindow call.
// Register the window class and return success/failure code.
return (RegisterClass(&wc)); }
//**********************************************************************
//
// CSimpleApp::fInitInstance
//
// Purpose:
//
// Instance initialization.
//
// Parameters:
//
// HANDLE hInstance - App. Instance Handle.
//
// int nCmdShow - Show parameter from WinMain
//
// Return Value:
//
// TRUE - Initialization Successful
// FALSE - Initialization Failed.
//
//
// Function Calls:
// Function Location
//
// CreateWindow Windows API
// ShowWindow Windows API
// UpdateWindow Windows API
// GetProfileInt Windows API
// OleBuildVersion OLE API
// OleInitialize OLE API
// OleStdCreateDbAlloc OLE2UI
//
// Comments:
//
// Note that successful Initalization of the OLE libraries
// is remembered so the UnInit is only called if needed.
//
//********************************************************************
BOOL CSimpleApp::fInitInstance (HANDLE hInstance, int nCmdShow) { LPMALLOC lpMalloc = NULL;
#ifndef WIN32
/* Since OLE is part of the operating system in Win32, we don't need to
* check the version number in Win32. */ DWORD dwVer = OleBuildVersion();
// check to see if we are compatible with this version of the libraries
if (HIWORD(dwVer) != rmm || LOWORD(dwVer) < rup) { #ifdef _DEBUG
TestDebugOut("WARNING: Incompatible OLE library version\r\n"); #else
return FALSE; #endif
} #endif // WIN32
#if defined( _DEBUG )
/* OLE2NOTE: Use a special debug allocator to help track down
** memory leaks. */ OleStdCreateDbAlloc(0, &lpMalloc); #endif
// We try passing in our own allocator first - if that fails we
// try without overriding the allocator.
if (SUCCEEDED(OleInitialize(lpMalloc)) || SUCCEEDED(OleInitialize(NULL))) { m_fInitialized = TRUE; }
#if defined( _DEBUG )
/* OLE2NOTE: release the special debug allocator so that only OLE is
** holding on to it. later when OleUninitialize is called, then ** the debug allocator object will be destroyed. when the debug ** allocator object is destoyed, it will report (to the Output ** Debug Terminal) whether there are any memory leaks. */ if (lpMalloc) lpMalloc->Release(); #endif
m_hInst = (HINSTANCE) hInstance;
// Create the "application" windows
m_hAppWnd = CreateWindow (TEXT("SimpDndAppWClass"), TEXT("Simple OLE 2.0 Drag/Drop Container"), WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, NULL, NULL, (HINSTANCE) hInstance, NULL);
if (!m_hAppWnd) return FALSE;
// if we have been launched by the test driver, tell it our window handle
if( m_hDriverWnd ) { PostMessage(m_hDriverWnd, WM_TESTREG, (WPARAM)m_hAppWnd, 0); }
// delay before dragging should start, in milliseconds
m_nDragDelay = GetProfileInt( TEXT("windows"), TEXT("DragDelay"), DD_DEFDRAGDELAY );
// minimum distance (radius) before drag should start, in pixels
m_nDragMinDist = GetProfileInt( TEXT("windows"), TEXT("DragMinDist"), DD_DEFDRAGMINDIST );
// delay before scrolling, in milliseconds
m_nScrollDelay = GetProfileInt( TEXT("windows"), TEXT("DragScrollDelay"), DD_DEFSCROLLDELAY );
// inset-width of the hot zone, in pixels
m_nScrollInset = GetProfileInt( TEXT("windows"), TEXT("DragScrollInset"), DD_DEFSCROLLINSET );
// scroll interval, in milliseconds
m_nScrollInterval = GetProfileInt( TEXT("windows"), TEXT("DragScrollInterval"), DD_DEFSCROLLINTERVAL );
ShowWindow (m_hAppWnd, nCmdShow); UpdateWindow (m_hAppWnd);
return m_fInitialized; }
//+-------------------------------------------------------------------------
//
// Member: CSimpleApp::UpdateDragDropEffects
//
// Synopsis: Update drag/drop effects
//
// Arguments: [iMenuPos] - menu position either source or target
// [iMenuCommand] - what command the menu selection maps to
// [dwEffect] - new effects
// [pdwEffectToUpdate] - where to store the effects
//
// Algorithm: Get the menu for either source or target. Then clear any
// outstanding check marks. Check the appropriate item. Finally
// update the effects that we allow.
//
// History: dd-mmm-yy Author Comment
// 06-May-94 Ricksa author
//
//--------------------------------------------------------------------------
void CSimpleApp::UpdateDragDropEffects( int iMenuPos, int iMenuCommand, DWORD dwEffect, DWORD *pdwEffectToUpdate) { // Get the menu that we want to process
HMENU hMenuItem = GetSubMenu(m_hHelpMenu, iMenuPos);
// Clear any current check marks
for (int i = 0; i < 3; i++) { CheckMenuItem(hMenuItem, i, MF_BYPOSITION | MF_UNCHECKED); }
// Check the appropriate item.
CheckMenuItem(hMenuItem, iMenuCommand, MF_BYCOMMAND | MF_CHECKED); *pdwEffectToUpdate = dwEffect; }
//**********************************************************************
//
// CSimpleApp::lCommandHandler
//
// Purpose:
//
// Handles the processing of WM_COMMAND.
//
// Parameters:
//
// HWND hWnd - Handle to the application Window
//
// UINT message - message (always WM_COMMAND)
//
// WPARAM wParam - Same as passed to the WndProc
//
// LPARAM lParam - Same as passed to the WndProc
//
// Return Value:
//
// NULL
//
// Function Calls:
// Function Location
//
// IOleObject::DoVerb Object
// GetClientRect Windows API
// MessageBox Windows API
// DialogBox Windows API
// MakeProcInstance Windows API
// FreeProcInstance Windows API
// SendMessage Windows API
// DefWindowProc Windows API
// CSimpleDoc::InsertObject DOC.CPP
// CSimpleDoc::CopyObjectToClip DOC.CPP
// CSimpleDoc::Close DOC.CPP
//
//********************************************************************
LRESULT CSimpleApp::lCommandHandler (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { RECT rect;
// see if the command is a verb selections
if (wParam >= IDM_VERB0) { // get the rectangle of the object
m_lpDoc->m_lpSite->GetObjRect(&rect);
if (m_lpDoc->m_lpSite->m_lpOleObject->DoVerb( wParam - IDM_VERB0, NULL, &m_lpDoc->m_lpSite->m_OleClientSite, -1, m_lpDoc->m_hDocWnd, &rect) != ResultFromScode(S_OK)) { TestDebugOut("Fail in IOleObject::DoVerb\n"); } } else { switch (wParam) { // bring up the About box
case IDM_ABOUT: { #ifdef WIN32
DialogBox(m_hInst, // current instance
TEXT("AboutBox"), // resource to use
m_hAppWnd, // parent handle
About); // About() instance address
#else
FARPROC lpProcAbout = MakeProcInstance((FARPROC)About, m_hInst);
DialogBox(m_hInst, // current instance
TEXT("AboutBox"), // resource to use
m_hAppWnd, // parent handle
lpProcAbout); // About() instance address
FreeProcInstance(lpProcAbout); #endif
break; }
// bring up the InsertObject Dialog
case IDM_INSERTOBJECT: m_lpDoc->InsertObject(); break;
// Copy the object to the Clipboard
case IDM_COPY: m_lpDoc->CopyObjectToClip(); break;
// exit the application
case IDM_EXIT: SendMessage(hWnd, WM_SYSCOMMAND, SC_CLOSE, 0L); break;
case IDM_NEW: lCreateDoc(hWnd, 0, 0, 0); break;
// Only allow copy from the source
case IDM_SOURCE_COPY: UpdateDragDropEffects(SOURCE_EFFECTS_MENU_POS, IDM_SOURCE_COPY, DROPEFFECT_COPY, &m_dwSourceEffect); break;
// Only allow move from the source
case IDM_SOURCE_MOVE: UpdateDragDropEffects(SOURCE_EFFECTS_MENU_POS, IDM_SOURCE_MOVE, DROPEFFECT_MOVE, &m_dwSourceEffect); break;
// Allow both copy and move from the source
case IDM_SOURCE_COPYMOVE: UpdateDragDropEffects(SOURCE_EFFECTS_MENU_POS, IDM_SOURCE_COPYMOVE, DROPEFFECT_COPY | DROPEFFECT_MOVE, &m_dwSourceEffect); break;
// Only accept copy in target
case IDM_TARGET_COPY: UpdateDragDropEffects(TARGET_EFFECTS_MENU_POS, IDM_TARGET_COPY, DROPEFFECT_COPY, &m_dwTargetEffect); break;
// Only accept move in target
case IDM_TARGET_MOVE: UpdateDragDropEffects(TARGET_EFFECTS_MENU_POS, IDM_TARGET_MOVE, DROPEFFECT_MOVE, &m_dwTargetEffect); break;
// Accept both move and copy in the target
case IDM_TARGET_COPYMOVE: UpdateDragDropEffects(TARGET_EFFECTS_MENU_POS, IDM_TARGET_COPYMOVE, DROPEFFECT_COPY | DROPEFFECT_MOVE, &m_dwTargetEffect); break;
default: return (DefWindowProc(hWnd, message, wParam, lParam)); } // end of switch
} // end of else
return NULL; }
//**********************************************************************
//
// CSimpleApp::lSizeHandler
//
// Purpose:
//
// Handles the WM_SIZE message
//
// Parameters:
//
// HWND hWnd - Handle to the application Window
//
// UINT message - message (always WM_SIZE)
//
// WPARAM wParam - Same as passed to the WndProc
//
// LPARAM lParam - Same as passed to the WndProc
//
// Return Value:
//
// LONG - returned from the "document" resizing
//
// Function Calls:
// Function Location
//
// GetClientRect Windows API
// CSimpleDoc::lResizeDoc DOC.CPP
//
//
//********************************************************************
long CSimpleApp::lSizeHandler (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { RECT rect;
GetClientRect(m_hAppWnd, &rect); return m_lpDoc->lResizeDoc(&rect); }
//**********************************************************************
//
// CSimpleApp::lCreateDoc
//
// Purpose:
//
// Handles the creation of a document object.
//
// Parameters:
//
// HWND hWnd - Handle to the application Window
//
// UINT message - message (always WM_CREATE)
//
// WPARAM wParam - Same as passed to the WndProc
//
// LPARAM lParam - Same as passed to the WndProc
//
// Return Value:
//
// NULL
//
// Function Calls:
// Function Location
//
// GetClientRect Windows API
// CSimpleDoc::CSimpleDoc DOC.CPP
//
//
//********************************************************************
long CSimpleApp::lCreateDoc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam) { RECT rect; static BOOL fFirstTime = TRUE;
if (m_lpDoc != NULL) { // There is a document defined already so we close it without
// saving which is equivalent to deleting the object.
m_lpDoc->Close(); m_lpDoc = NULL; }
GetClientRect(hWnd, &rect);
m_lpDoc = CSimpleDoc::Create(this, &rect, hWnd);
// First time initialization - for some reason the doc sets the
// the application's m_hHelpMenu which we need. So we do the
// initialization here.
if (fFirstTime) { fFirstTime = FALSE;
// Check default allowed effects for the source
UpdateDragDropEffects(SOURCE_EFFECTS_MENU_POS, IDM_SOURCE_COPYMOVE, m_dwSourceEffect, &m_dwSourceEffect);
// Check default allowed effects for the target
UpdateDragDropEffects(TARGET_EFFECTS_MENU_POS, IDM_TARGET_COPYMOVE, m_dwTargetEffect, &m_dwTargetEffect); }
return NULL; }
//**********************************************************************
//
// CSimpleApp::HandleAccelerators
//
// Purpose:
//
// To properly handle accelerators in the Message Loop
//
// Parameters:
//
// LPMSG lpMsg - A pointer to the message structure.
//
// Return Value:
//
// TRUE - The accelerator was handled
// FALSE - The accelerator was not handled
//
// Function Calls:
// Function Location
//
//
//********************************************************************
BOOL CSimpleApp::HandleAccelerators(LPMSG lpMsg) { BOOL retval = FALSE;
// we do not have any accelerators
return retval; }
//**********************************************************************
//
// CSimpleApp::PaintApp
//
// Purpose:
//
// Handles the painting of the doc window.
//
//
// Parameters:
//
// HDC hDC - hDC to the Doc Window.
//
// Return Value:
//
// None
//
// Function Calls:
// Function Location
//
// CSimpleDoc::PaintDoc DOC.CPP
//
// Comments:
//
// This is an app level function in case we want to do palette
// management.
//
//********************************************************************
void CSimpleApp::PaintApp (HDC hDC) { // at this level, we could enumerate through all of the
// visible objects in the application, so that a palette
// that best fits all of the objects can be built.
// This app is designed to take on the same palette
// functionality that was provided in OLE 1.0, the palette
// of the last object drawn is realized. Since we only
// support one object at a time, it shouldn't be a big
// deal.
// if we supported multiple documents, we would enumerate
// through each of the open documents and call paint.
if (m_lpDoc) { m_lpDoc->PaintDoc(hDC); }
}
|