357 lines
7.7 KiB
C++
357 lines
7.7 KiB
C++
/***
|
|
*cpoint.cpp
|
|
*
|
|
* Copyright (C) 1992-1994, Microsoft Corporation. All Rights Reserved.
|
|
*
|
|
*Purpose:
|
|
* This module implements the CPoint and CPointCF classes.
|
|
*
|
|
* This module is intended as a sample implementation of the IDispatch
|
|
* interface, and its purpose is to demonstrate how an object can
|
|
* expose methods and properties for programatic and cross-process
|
|
* access via the IDispatch interface.
|
|
*
|
|
*Implementation Notes:
|
|
*
|
|
*****************************************************************************/
|
|
|
|
#include "spoly.h"
|
|
#include "cpoint.h"
|
|
|
|
|
|
CPoint::CPoint()
|
|
{
|
|
m_x = 0;
|
|
m_y = 0;
|
|
m_refs = 0;
|
|
m_ptinfo = NULL;
|
|
}
|
|
|
|
/***
|
|
*CPoint::Create(void)
|
|
*Purpose:
|
|
* Create an instance of a CPoint object.
|
|
*
|
|
*Entry:
|
|
* None
|
|
*
|
|
*Exit:
|
|
* returns a CPoint*, NULL if creation failed.
|
|
*
|
|
***********************************************************************/
|
|
CPoint FAR*
|
|
CPoint::Create()
|
|
{
|
|
HRESULT hresult;
|
|
CPoint FAR* ppoint;
|
|
ITypeInfo FAR* ptinfo;
|
|
extern INTERFACEDATA NEAR g_idataCPoint;
|
|
|
|
|
|
if((ppoint = new FAR CPoint()) == NULL)
|
|
return NULL;
|
|
ppoint->AddRef();
|
|
|
|
hresult =
|
|
CreateDispTypeInfo(&g_idataCPoint, LOCALE_SYSTEM_DEFAULT, &ptinfo);
|
|
if(hresult != NOERROR)
|
|
goto LError0;
|
|
|
|
ppoint->m_ptinfo = ptinfo;
|
|
|
|
return ppoint;
|
|
|
|
LError0:;
|
|
ppoint->Release();
|
|
|
|
return NULL;
|
|
}
|
|
|
|
|
|
//---------------------------------------------------------------------
|
|
// IUnknown Methods
|
|
//---------------------------------------------------------------------
|
|
|
|
|
|
STDMETHODIMP
|
|
CPoint::QueryInterface(REFIID riid, void FAR* FAR* ppv)
|
|
{
|
|
if(IsEqualIID(riid, IID_IUnknown) || IsEqualIID(riid, IID_IDispatch)){
|
|
*ppv = this;
|
|
AddRef();
|
|
return NOERROR;
|
|
}
|
|
*ppv = NULL;
|
|
return ResultFromScode(E_NOINTERFACE);
|
|
}
|
|
|
|
|
|
STDMETHODIMP_(unsigned long)
|
|
CPoint::AddRef(void)
|
|
{
|
|
return ++m_refs;
|
|
}
|
|
|
|
|
|
STDMETHODIMP_(unsigned long)
|
|
CPoint::Release(void)
|
|
{
|
|
if(--m_refs == 0){
|
|
if(m_ptinfo != NULL){
|
|
m_ptinfo->Release();
|
|
}
|
|
delete this;
|
|
return 0;
|
|
}
|
|
return m_refs;
|
|
}
|
|
|
|
|
|
//---------------------------------------------------------------------
|
|
// IDispatch methods
|
|
//---------------------------------------------------------------------
|
|
|
|
|
|
STDMETHODIMP
|
|
CPoint::GetTypeInfoCount(unsigned int FAR* pctinfo)
|
|
{
|
|
// this object has a single *introduced* interface
|
|
//
|
|
*pctinfo = 1;
|
|
|
|
return NOERROR;
|
|
}
|
|
|
|
|
|
STDMETHODIMP
|
|
CPoint::GetTypeInfo(unsigned int itinfo, LCID lcid, ITypeInfo FAR* FAR* pptinfo)
|
|
{
|
|
UNUSED(lcid);
|
|
|
|
if(itinfo != 0)
|
|
return ResultFromScode(DISP_E_BADINDEX);
|
|
|
|
m_ptinfo->AddRef();
|
|
*pptinfo = m_ptinfo;
|
|
|
|
return NOERROR;
|
|
}
|
|
|
|
|
|
/***
|
|
*HRESULT CPoint::GetIDsOfNames(REFIID, char**, unsigned int, LCID, DISPID*)
|
|
*Purpose:
|
|
* This method translates the given array of names to a corresponding
|
|
* array of DISPIDs.
|
|
*
|
|
* Index 0 of the name array is the member name, and indices 1-N if
|
|
* present represent named parameters on that member.
|
|
*
|
|
* The local ID ('lcid') is unused by this naive implementation. A more
|
|
* sophisticated implementation, sensitive to localization and natural
|
|
* language support would use the locale ID to interpret the given names
|
|
* in a correct locale specific context.
|
|
*
|
|
*Entry:
|
|
* rgszNames = pointer to an array of names
|
|
* cNames = the number of names in the rgszNames array
|
|
* lcid = the callers locale ID
|
|
*
|
|
*Exit:
|
|
* return value = HRESULT
|
|
* rgid = array of name IDs corresponding to the rgszNames array
|
|
* this array will contain -1 for each entry that is not known.
|
|
*
|
|
***********************************************************************/
|
|
STDMETHODIMP
|
|
CPoint::GetIDsOfNames(
|
|
REFIID riid,
|
|
OLECHAR FAR* FAR* rgszNames,
|
|
unsigned int cNames,
|
|
LCID lcid,
|
|
DISPID FAR* rgdispid)
|
|
{
|
|
UNUSED(lcid);
|
|
|
|
if(!IsEqualIID(riid,IID_NULL))
|
|
return ResultFromScode(DISP_E_UNKNOWNINTERFACE);
|
|
|
|
return DispGetIDsOfNames(m_ptinfo, rgszNames, cNames, rgdispid);
|
|
}
|
|
|
|
|
|
/***
|
|
*HRESULT CPoint::Invoke(...)
|
|
*Purpose:
|
|
* Dispatch a method or property request for objects of type CPoint.
|
|
*
|
|
* see the IDispatch document for more information, and a general
|
|
* description of this method.
|
|
*
|
|
*Entry:
|
|
* dispidMember = the DISPID of the member being requested
|
|
*
|
|
* riid = reference to the interface ID of the interface on this object
|
|
* that the requested member belongs to. IID_NULL means to interpret
|
|
* the member as belonging to the implementation defined "default"
|
|
* or "primary" interface.
|
|
*
|
|
* lcid = the caller's locale ID
|
|
*
|
|
* wFlags = flags indicating the type of access being requested
|
|
*
|
|
* pdispparams = pointer to the DISPPARAMS struct containing the
|
|
* requested members arguments (if any) and its named parameter
|
|
* DISPIDs (if any).
|
|
*
|
|
*Exit:
|
|
* return value = HRESULT
|
|
* see the IDispatch spec for a description of possible success codes.
|
|
*
|
|
* pvarResult = pointer to a caller allocated VARIANT containing
|
|
* the members return value (if any).
|
|
*
|
|
* pexcepinfo = caller allocated exception info structure, this will
|
|
* be filled in only if an exception was raised that must be passed
|
|
* up through Invoke to an enclosing handler.
|
|
*
|
|
* puArgErr = pointer to a caller allocated UINT, that will contain the
|
|
* index of the offending argument if a DISP_E_TYPEMISMATCH error
|
|
* was returned indicating that one of the arguments was of an
|
|
* incorrect type and/or could not be reasonably coerced to a proper
|
|
* type.
|
|
*
|
|
***********************************************************************/
|
|
STDMETHODIMP
|
|
CPoint::Invoke(
|
|
DISPID dispidMember,
|
|
REFIID riid,
|
|
LCID lcid,
|
|
unsigned short wFlags,
|
|
DISPPARAMS FAR* pdispparams,
|
|
VARIANT FAR* pvarResult,
|
|
EXCEPINFO FAR* pexcepinfo,
|
|
unsigned int FAR* puArgErr)
|
|
{
|
|
UNUSED(lcid);
|
|
|
|
if(!IsEqualIID(riid, IID_NULL))
|
|
return ResultFromScode(DISP_E_UNKNOWNINTERFACE);
|
|
|
|
return DispInvoke(
|
|
this, m_ptinfo,
|
|
dispidMember, wFlags, pdispparams,
|
|
pvarResult, pexcepinfo, puArgErr);
|
|
}
|
|
|
|
|
|
//---------------------------------------------------------------------
|
|
// Introduced methods
|
|
//---------------------------------------------------------------------
|
|
|
|
short METHODCALLTYPE EXPORT
|
|
CPoint::GetX()
|
|
{
|
|
return m_x;
|
|
}
|
|
|
|
void METHODCALLTYPE EXPORT
|
|
CPoint::SetX(short x)
|
|
{
|
|
m_x = x;
|
|
}
|
|
|
|
short METHODCALLTYPE EXPORT
|
|
CPoint::GetY()
|
|
{
|
|
return m_y;
|
|
}
|
|
|
|
void METHODCALLTYPE EXPORT
|
|
CPoint::SetY(short y)
|
|
{
|
|
m_y = y;
|
|
}
|
|
|
|
|
|
//---------------------------------------------------------------------
|
|
// Implementation of the CPoint Class Factory
|
|
//---------------------------------------------------------------------
|
|
|
|
CPointCF::CPointCF()
|
|
{
|
|
m_refs = 0;
|
|
}
|
|
|
|
IClassFactory FAR*
|
|
CPointCF::Create()
|
|
{
|
|
CPointCF FAR* pCF;
|
|
|
|
if((pCF = new FAR CPointCF()) == NULL)
|
|
return NULL;
|
|
pCF->AddRef();
|
|
return pCF;
|
|
}
|
|
|
|
STDMETHODIMP
|
|
CPointCF::QueryInterface(REFIID riid, void FAR* FAR* ppv)
|
|
{
|
|
if(IsEqualIID(riid, IID_IUnknown) || IsEqualIID(riid, IID_IClassFactory)){
|
|
*ppv = this;
|
|
++m_refs;
|
|
return NOERROR;
|
|
}
|
|
*ppv = NULL;
|
|
return ResultFromScode(E_NOINTERFACE);
|
|
}
|
|
|
|
STDMETHODIMP_(unsigned long)
|
|
CPointCF::AddRef(void)
|
|
{
|
|
return ++m_refs;
|
|
}
|
|
|
|
STDMETHODIMP_(unsigned long)
|
|
CPointCF::Release(void)
|
|
{
|
|
if(--m_refs == 0){
|
|
delete this;
|
|
return 0;
|
|
}
|
|
return m_refs;
|
|
}
|
|
|
|
STDMETHODIMP
|
|
CPointCF::CreateInstance(
|
|
IUnknown FAR* punkOuter,
|
|
REFIID riid,
|
|
void FAR* FAR* ppv)
|
|
{
|
|
HRESULT hresult;
|
|
CPoint FAR *ppoint;
|
|
|
|
UNUSED(punkOuter);
|
|
|
|
if((ppoint = CPoint::Create()) == NULL){
|
|
*ppv = NULL;
|
|
return ResultFromScode(E_OUTOFMEMORY);
|
|
}
|
|
hresult = ppoint->QueryInterface(riid, ppv);
|
|
ppoint->Release();
|
|
return hresult;
|
|
}
|
|
|
|
STDMETHODIMP
|
|
#ifdef _MAC
|
|
CPointCF::LockServer(unsigned long fLock)
|
|
#else
|
|
CPointCF::LockServer(BOOL fLock)
|
|
#endif
|
|
{
|
|
UNUSED(fLock);
|
|
|
|
return NOERROR;
|
|
}
|
|
|