我认为这是《Visual c++技术内幕》这本书中讲的最为出色的一个示例,将COM的“面向接口”的思路讲述得相当清晰,再加上嵌套类和引用计数的使用,让COM初学者能一窥其实质。
就我的理解,COM就好比是一瓶“胶水“,把客户exe同所需要的DLL或者其他exe”黏合“起来,而这些工作对客户来说是透明的,客户只是按双方协商好的协议,使用特定的接口就行了,只要接口保持不变,客户就不需要跟随DLL等的变化而变化,是为”面向接口“,这一切都是COM的功劳,而且COM使用包容和集合来代替继承,更加符合面向对象的思想。
// client.cpp pseudo-OLE command-line application
Code
<!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>-->#include<stdio.h>
#include<stddef.h>//foroffsetofinMETHOD_PROLOGUE
#include<assert.h>
#include"interface.h"
//----------mainprogram-----------------------------------------------
intmain()//simulatesOLEclientprogram
{
TRACE("6Enteringclientmain/n");//第6步
IUnknown*pUnk;//Ifyoudeclarethesevoid*,youlosetype-safety
IMotion*pMot;
IVisual*pVis;
IClassFactory*pClf;
GetClassObject(CLSID_CSpaceship,IID_IClassFactory,(void**)&pClf);
pClf->CreateInstance(IID_IUnknown,(void**)&pUnk);
pUnk->QueryInterface(IID_IMotion,(void**)&pMot);//Allthreepointersshouldwork
pMot->QueryInterface(IID_IVisual,(void**)&pVis);//
TRACE("23main:pUnk=%p,pMot=%p,pDis=%p/n",pUnk,pMot,pVis);//第23步
//Testalltheinterfacevirtualfunctions
pMot->Fly();
intnPos=pMot->GetPosition();
TRACE("32nPos=%d/n",nPos);//第32步
pVis->Display();
pClf->Release();
pUnk->Release();
pMot->Release();
pVis->Release();
return0;
}
<!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>-->#include<stdio.h>
#include<stddef.h>//foroffsetofinMETHOD_PROLOGUE
#include<assert.h>
#include"interface.h"
//----------mainprogram-----------------------------------------------
intmain()//simulatesOLEclientprogram
{
TRACE("6Enteringclientmain/n");//第6步
IUnknown*pUnk;//Ifyoudeclarethesevoid*,youlosetype-safety
IMotion*pMot;
IVisual*pVis;
IClassFactory*pClf;
GetClassObject(CLSID_CSpaceship,IID_IClassFactory,(void**)&pClf);
pClf->CreateInstance(IID_IUnknown,(void**)&pUnk);
pUnk->QueryInterface(IID_IMotion,(void**)&pMot);//Allthreepointersshouldwork
pMot->QueryInterface(IID_IVisual,(void**)&pVis);//
TRACE("23main:pUnk=%p,pMot=%p,pDis=%p/n",pUnk,pMot,pVis);//第23步
//Testalltheinterfacevirtualfunctions
pMot->Fly();
intnPos=pMot->GetPosition();
TRACE("32nPos=%d/n",nPos);//第32步
pVis->Display();
pClf->Release();
pUnk->Release();
pMot->Release();
pVis->Release();
return0;
}
// interface.h
definitions that make our code look like MFC code
Code
<!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>-->#defineBOOLint
#defineDWORDunsignedint
#defineTRUE1
#defineFALSE0
#defineTRACEprintf
#defineASSERTassert
//----------definitionsandmacros-----------------------------------
#defineCLSID_CSpaceship10
#defineIID_IUnknown0
#defineIID_IClassFactory1
#defineIID_IMotion2
#defineIID_IVisual3
//thismacrofor16-bitWindowsonly
#defineMETHOD_PROLOGUE(theClass,localClass)/
theClass*pThis=((theClass*)((char*)(this)-/
offsetof(theClass,m_x##localClass)));/
BOOLGetClassObject(intnClsid,intnIid,void**ppvObj);
//----------interfacedeclarations-----------------------------------
structIUnknown
{
IUnknown()
{
TRACE("21013EnteringIUnknownctor%p/n",this);//第2步//第10步//第13步
}
virtualBOOLQueryInterface(intnIid,void**ppvObj)=0;
virtualDWORDRelease()=0;
virtualDWORDAddRef()=0;
};
structIClassFactory:publicIUnknown
{
IClassFactory()
{
TRACE("3EnteringIClassFactoryctor%p/n",this);//第3步
}
virtualBOOLCreateInstance(intnIid,void**ppvObj)=0;
};
structIMotion:publicIUnknown
{
IMotion()
{
TRACE("11EnteringIMotionctor%p/n",this);//第11步
}
virtualvoidFly()=0;//pure
virtualint&GetPosition()=0;
};
structIVisual:publicIUnknown
{
IVisual()
{
TRACE("14EnteringIVisualctor%p/n",this);//第14步
}
virtualvoidDisplay()=0;
};
classCSimulatedCmdTarget//'simulated'CSimulatedCmdTarget
{
public:
DWORDm_dwRef;
protected:
CSimulatedCmdTarget()
{
TRACE("19EnteringCSimulatedCmdTargetctor%p/n",this);//第1步//第9步
m_dwRef=1;//impliedfirstAddRef
}
virtual~CSimulatedCmdTarget()
{
TRACE("4749EnteringCSimulatedCmdTargetdtor%p/n",this);//第47步//第49步
}
DWORDExternalRelease()
{
//第18步//第38步//第40步//第42步//第44步
TRACE("1838404244EnteringCSimulatedCmdTarget::ExternalRelease--RefCount=%ld/n",m_dwRef);
if(m_dwRef==0)
return0;
if(--m_dwRef==0L)
{
TRACE("45deleting/n");//第45步
deletethis;
return0;
}
returnm_dwRef;
}
DWORDExternalAddRef()
{
return++m_dwRef;
}
};
<!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>-->#defineBOOLint
#defineDWORDunsignedint
#defineTRUE1
#defineFALSE0
#defineTRACEprintf
#defineASSERTassert
//----------definitionsandmacros-----------------------------------
#defineCLSID_CSpaceship10
#defineIID_IUnknown0
#defineIID_IClassFactory1
#defineIID_IMotion2
#defineIID_IVisual3
//thismacrofor16-bitWindowsonly
#defineMETHOD_PROLOGUE(theClass,localClass)/
theClass*pThis=((theClass*)((char*)(this)-/
offsetof(theClass,m_x##localClass)));/
BOOLGetClassObject(intnClsid,intnIid,void**ppvObj);
//----------interfacedeclarations-----------------------------------
structIUnknown
{
IUnknown()
{
TRACE("21013EnteringIUnknownctor%p/n",this);//第2步//第10步//第13步
}
virtualBOOLQueryInterface(intnIid,void**ppvObj)=0;
virtualDWORDRelease()=0;
virtualDWORDAddRef()=0;
};
structIClassFactory:publicIUnknown
{
IClassFactory()
{
TRACE("3EnteringIClassFactoryctor%p/n",this);//第3步
}
virtualBOOLCreateInstance(intnIid,void**ppvObj)=0;
};
structIMotion:publicIUnknown
{
IMotion()
{
TRACE("11EnteringIMotionctor%p/n",this);//第11步
}
virtualvoidFly()=0;//pure
virtualint&GetPosition()=0;
};
structIVisual:publicIUnknown
{
IVisual()
{
TRACE("14EnteringIVisualctor%p/n",this);//第14步
}
virtualvoidDisplay()=0;
};
classCSimulatedCmdTarget//'simulated'CSimulatedCmdTarget
{
public:
DWORDm_dwRef;
protected:
CSimulatedCmdTarget()
{
TRACE("19EnteringCSimulatedCmdTargetctor%p/n",this);//第1步//第9步
m_dwRef=1;//impliedfirstAddRef
}
virtual~CSimulatedCmdTarget()
{
TRACE("4749EnteringCSimulatedCmdTargetdtor%p/n",this);//第47步//第49步
}
DWORDExternalRelease()
{
//第18步//第38步//第40步//第42步//第44步
TRACE("1838404244EnteringCSimulatedCmdTarget::ExternalRelease--RefCount=%ld/n",m_dwRef);
if(m_dwRef==0)
return0;
if(--m_dwRef==0L)
{
TRACE("45deleting/n");//第45步
deletethis;
return0;
}
returnm_dwRef;
}
DWORDExternalAddRef()
{
return++m_dwRef;
}
};
// Spaceship.h
Code
<!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>-->classCSpaceship;
//----------classdeclarations-----------------------------------------------
classCSpaceshipFactory:publicCSimulatedCmdTarget
{
public:
CSpaceshipFactory()
{
TRACE("5EnteringCSpaceshipFactoryctor%p/n",this);//第5步
}
~CSpaceshipFactory()
{
TRACE("48EnteringCSpaceshipFactorydtor%p/n",this);//第48步
}
BOOLExternalQueryInterface(intlRid,void**ppvObj);
classXClassFactory:publicIClassFactory
{
public:
XClassFactory()
{
TRACE("4EnteringXClassFactoryctor%p/n",this);//第4步
}
virtualBOOLQueryInterface(intlRid,void**ppvObj);
virtualDWORDRelease();
virtualDWORDAddRef();
virtualBOOLCreateInstance(intlRid,void**ppvObj);
}m_xClassFactory;
friendclassXClassFactory;
};
classCSpaceship:publicCSimulatedCmdTarget
{
private:
intm_nPosition;//Wecanaccessthesefromalltheinterfaces
intm_nAcceleration;
intm_nColor;
public:
CSpaceship()
{
TRACE("16EnteringCSpaceshipctor%p/n",this);//第16步
m_nPosition=100;
m_nAcceleration=101;
m_nColor=102;
}
~CSpaceship()
{
TRACE("46EnteringCSpaceshipdtor%p/n",this);//第46步
}
BOOLExternalQueryInterface(intlRid,void**ppvObj);
classXMotion:publicIMotion
{
public:
XMotion()
{
TRACE("12EnteringXMotionctor%p/n",this);//第12步
}
virtualBOOLQueryInterface(intlRid,void**ppvObj);
virtualDWORDRelease();
virtualDWORDAddRef();
virtualvoidFly();
virtualint&GetPosition();
}m_xMotion;
classXVisual:publicIVisual
{
public:
XVisual()
{
TRACE("15EnteringXVisualctor/n");//第15步
}
virtualBOOLQueryInterface(intlRid,void**ppvObj);
virtualDWORDRelease();
virtualDWORDAddRef();
virtualvoidDisplay();
}m_xVisual;
friendclassXVisual;//Thesemustbeatthebottom!
friendclassXMotion;
friendclassCSpaceshipFactory::XClassFactory;
};
<!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>-->classCSpaceship;
//----------classdeclarations-----------------------------------------------
classCSpaceshipFactory:publicCSimulatedCmdTarget
{
public:
CSpaceshipFactory()
{
TRACE("5EnteringCSpaceshipFactoryctor%p/n",this);//第5步
}
~CSpaceshipFactory()
{
TRACE("48EnteringCSpaceshipFactorydtor%p/n",this);//第48步
}
BOOLExternalQueryInterface(intlRid,void**ppvObj);
classXClassFactory:publicIClassFactory
{
public:
XClassFactory()
{
TRACE("4EnteringXClassFactoryctor%p/n",this);//第4步
}
virtualBOOLQueryInterface(intlRid,void**ppvObj);
virtualDWORDRelease();
virtualDWORDAddRef();
virtualBOOLCreateInstance(intlRid,void**ppvObj);
}m_xClassFactory;
friendclassXClassFactory;
};
classCSpaceship:publicCSimulatedCmdTarget
{
private:
intm_nPosition;//Wecanaccessthesefromalltheinterfaces
intm_nAcceleration;
intm_nColor;
public:
CSpaceship()
{
TRACE("16EnteringCSpaceshipctor%p/n",this);//第16步
m_nPosition=100;
m_nAcceleration=101;
m_nColor=102;
}
~CSpaceship()
{
TRACE("46EnteringCSpaceshipdtor%p/n",this);//第46步
}
BOOLExternalQueryInterface(intlRid,void**ppvObj);
classXMotion:publicIMotion
{
public:
XMotion()
{
TRACE("12EnteringXMotionctor%p/n",this);//第12步
}
virtualBOOLQueryInterface(intlRid,void**ppvObj);
virtualDWORDRelease();
virtualDWORDAddRef();
virtualvoidFly();
virtualint&GetPosition();
}m_xMotion;
classXVisual:publicIVisual
{
public:
XVisual()
{
TRACE("15EnteringXVisualctor/n");//第15步
}
virtualBOOLQueryInterface(intlRid,void**ppvObj);
virtualDWORDRelease();
virtualDWORDAddRef();
virtualvoidDisplay();
}m_xVisual;
friendclassXVisual;//Thesemustbeatthebottom!
friendclassXMotion;
friendclassCSpaceshipFactory::XClassFactory;
};
// Spaceship.cpp pseudo-OLE command-line application
Code
<!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>-->#include<stdio.h>
#include<stddef.h>//foroffsetofinMETHOD_PROLOGUE
#include<ASSERT.h>
#include"Interface.h"
#include"Spaceship.h"
CSpaceshipFactoryg_factory;
//----------memberfunctions-----------------------------------------
BOOLCSpaceshipFactory::ExternalQueryInterface(intnIid,void**ppvObj)
{
TRACE("7EnteringCSpaceshipFactory::ExternalQueryInterface--nIid=%d/n",nIid);//第7步
switch(nIid)
{
caseIID_IUnknown:
caseIID_IClassFactory:
*ppvObj=&m_xClassFactory;
break;
default:
*ppvObj=NULL;
returnFALSE;
}
ExternalAddRef();
returnTRUE;
}
BOOLCSpaceshipFactory::XClassFactory::QueryInterface(intnIid,void**ppvObj)
{
TRACE("EnteringCSpaceshipFactory::XClassFactory::QueryInterface--nIid=%d/n",nIid);
METHOD_PROLOGUE(CSpaceshipFactory,ClassFactory)//makespThis
returnpThis->ExternalQueryInterface(nIid,ppvObj);//delegatetoCSpaceshipFactory
}
BOOLCSpaceshipFactory::XClassFactory::CreateInstance(intnIid,void**ppvObj)
{
TRACE("8EnteringCSpaceshipFactory::XClassFactory::CreateInstance/n");//第8步
METHOD_PROLOGUE(CSpaceshipFactory,ClassFactory)//makespThis
CSpaceship*pObj=newCSpaceship();
if(pObj->ExternalQueryInterface(nIid,ppvObj))
{
pObj->ExternalRelease();//balancereferencecount
returnTRUE;
}
returnFALSE;
}
DWORDCSpaceshipFactory::XClassFactory::Release()
{
TRACE("37EnteringCSpaceshipFactory::XClassFactory::Release/n");//第37步
METHOD_PROLOGUE(CSpaceshipFactory,ClassFactory)//makespThis
returnpThis->ExternalRelease();//delegatetoCSimulatedCmdTarget
}
DWORDCSpaceshipFactory::XClassFactory::AddRef()
{
TRACE("EnteringCSpaceshipFactory::XClassFactory::AddRef/n");
METHOD_PROLOGUE(CSpaceshipFactory,ClassFactory)//makespThis
returnpThis->ExternalAddRef();//delegatetoCSimulatedCmdTarget
}
BOOLCSpaceship::ExternalQueryInterface(intnIid,void**ppvObj)
{
TRACE("172022EnteringCSpaceship::ExternalQueryInterface--nIid=%d/n",nIid);//第17步//第20步//第22步
switch(nIid)
{
caseIID_IUnknown:
caseIID_IMotion:
*ppvObj=&m_xMotion;//BothIMotionandIVisualarederived
break;//fromIUnknown,soeitherpointerwilldo
caseIID_IVisual:
*ppvObj=&m_xVisual;
break;
default:
*ppvObj=NULL;
returnFALSE;
}
ExternalAddRef();
returnTRUE;
}
BOOLCSpaceship::XMotion::QueryInterface(intnIid,void**ppvObj){
TRACE("1921EnteringCSpaceship::XMotion::QueryInterface--nIid=%d/n",nIid);//第19步//第21步
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
returnpThis->ExternalQueryInterface(nIid,ppvObj);//delegatetoCSpaceship
}
DWORDCSpaceship::XMotion::Release(){
TRACE("3941EnteringCSpaceship::XMotion::Release/n");//第39步//第41步
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
returnpThis->ExternalRelease();//delegatetoCSimulatedCmdTarget
}
DWORDCSpaceship::XMotion::AddRef(){
TRACE("EnteringCSpaceship::XMotion::AddRef/n");
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
returnpThis->ExternalAddRef();//delegatetoCSimulatedCmdTarget
}
voidCSpaceship::XMotion::Fly(){
TRACE("24EnteringCSpaceship::XMotion::Fly/n");//第24步
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
TRACE("25this=%p,pThis=%p/n",this,pThis);//第25步
TRACE("26m_nPosition=%d/n",pThis->m_nPosition);//第26步
TRACE("27m_nAcceleration=%d/n",pThis->m_nAcceleration);//第27步
}
int&CSpaceship::XMotion::GetPosition(){
TRACE("28EnteringCSpaceship::XMotion::GetPosition/n");//第28步
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
TRACE("29this=%p,pThis=%p/n",this,pThis);//第29步
TRACE("30m_nPosition=%d/n",pThis->m_nPosition);//第30步
TRACE("31m_nAcceleration=%d/n",pThis->m_nAcceleration);//第31步
returnpThis->m_nPosition;
}
BOOLCSpaceship::XVisual::QueryInterface(intnIid,void**ppvObj){
TRACE("EnteringCSpaceship::XVisual::QueryInterface--nIid=%d/n",nIid);
METHOD_PROLOGUE(CSpaceship,Visual)//makespThis
returnpThis->ExternalQueryInterface(nIid,ppvObj);//delegateto
//CSpaceship
}
DWORDCSpaceship::XVisual::Release(){
TRACE("43EnteringCSpaceship::XVisual::Release/n");//第43步
METHOD_PROLOGUE(CSpaceship,Visual)//makespThis
returnpThis->ExternalRelease();//delegatetoCSimulatedCmdTarget
}
DWORDCSpaceship::XVisual::AddRef(){
TRACE("EnteringCSpaceship::XVisual::AddRef/n");
METHOD_PROLOGUE(CSpaceship,Visual)//makespThis
returnpThis->ExternalAddRef();//delegatetoCSimulatedCmdTarget
}
voidCSpaceship::XVisual::Display(){
TRACE("33EnteringCSpaceship::XVisual::Display/n");//第33步
METHOD_PROLOGUE(CSpaceship,Visual)//makespThis
TRACE("34this=%p,pThis=%p/n",this,pThis);//第34步
TRACE("35m_nPosition=%d/n",pThis->m_nPosition);//第35步
TRACE("36m_nColor=%d/n",pThis->m_nColor);//第36步
}
//----------simulatesCOMcomponent----------------------------------
//InrealCOM,thiswouldbeDllGetClassObject,whichwouldbecalled
//wheneveraclientcalledCoGetClassObject
BOOLGetClassObject(intnClsid,intnIid,void**ppvObj)
{
ASSERT(nClsid==CLSID_CSpaceship);
ASSERT((nIid==IID_IUnknown)||(nIid==IID_IClassFactory));
returng_factory.ExternalQueryInterface(nIid,ppvObj);
//refcountis2,whichpreventsaccidentaldeletion
}
<!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>-->#include<stdio.h>
#include<stddef.h>//foroffsetofinMETHOD_PROLOGUE
#include<ASSERT.h>
#include"Interface.h"
#include"Spaceship.h"
CSpaceshipFactoryg_factory;
//----------memberfunctions-----------------------------------------
BOOLCSpaceshipFactory::ExternalQueryInterface(intnIid,void**ppvObj)
{
TRACE("7EnteringCSpaceshipFactory::ExternalQueryInterface--nIid=%d/n",nIid);//第7步
switch(nIid)
{
caseIID_IUnknown:
caseIID_IClassFactory:
*ppvObj=&m_xClassFactory;
break;
default:
*ppvObj=NULL;
returnFALSE;
}
ExternalAddRef();
returnTRUE;
}
BOOLCSpaceshipFactory::XClassFactory::QueryInterface(intnIid,void**ppvObj)
{
TRACE("EnteringCSpaceshipFactory::XClassFactory::QueryInterface--nIid=%d/n",nIid);
METHOD_PROLOGUE(CSpaceshipFactory,ClassFactory)//makespThis
returnpThis->ExternalQueryInterface(nIid,ppvObj);//delegatetoCSpaceshipFactory
}
BOOLCSpaceshipFactory::XClassFactory::CreateInstance(intnIid,void**ppvObj)
{
TRACE("8EnteringCSpaceshipFactory::XClassFactory::CreateInstance/n");//第8步
METHOD_PROLOGUE(CSpaceshipFactory,ClassFactory)//makespThis
CSpaceship*pObj=newCSpaceship();
if(pObj->ExternalQueryInterface(nIid,ppvObj))
{
pObj->ExternalRelease();//balancereferencecount
returnTRUE;
}
returnFALSE;
}
DWORDCSpaceshipFactory::XClassFactory::Release()
{
TRACE("37EnteringCSpaceshipFactory::XClassFactory::Release/n");//第37步
METHOD_PROLOGUE(CSpaceshipFactory,ClassFactory)//makespThis
returnpThis->ExternalRelease();//delegatetoCSimulatedCmdTarget
}
DWORDCSpaceshipFactory::XClassFactory::AddRef()
{
TRACE("EnteringCSpaceshipFactory::XClassFactory::AddRef/n");
METHOD_PROLOGUE(CSpaceshipFactory,ClassFactory)//makespThis
returnpThis->ExternalAddRef();//delegatetoCSimulatedCmdTarget
}
BOOLCSpaceship::ExternalQueryInterface(intnIid,void**ppvObj)
{
TRACE("172022EnteringCSpaceship::ExternalQueryInterface--nIid=%d/n",nIid);//第17步//第20步//第22步
switch(nIid)
{
caseIID_IUnknown:
caseIID_IMotion:
*ppvObj=&m_xMotion;//BothIMotionandIVisualarederived
break;//fromIUnknown,soeitherpointerwilldo
caseIID_IVisual:
*ppvObj=&m_xVisual;
break;
default:
*ppvObj=NULL;
returnFALSE;
}
ExternalAddRef();
returnTRUE;
}
BOOLCSpaceship::XMotion::QueryInterface(intnIid,void**ppvObj){
TRACE("1921EnteringCSpaceship::XMotion::QueryInterface--nIid=%d/n",nIid);//第19步//第21步
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
returnpThis->ExternalQueryInterface(nIid,ppvObj);//delegatetoCSpaceship
}
DWORDCSpaceship::XMotion::Release(){
TRACE("3941EnteringCSpaceship::XMotion::Release/n");//第39步//第41步
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
returnpThis->ExternalRelease();//delegatetoCSimulatedCmdTarget
}
DWORDCSpaceship::XMotion::AddRef(){
TRACE("EnteringCSpaceship::XMotion::AddRef/n");
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
returnpThis->ExternalAddRef();//delegatetoCSimulatedCmdTarget
}
voidCSpaceship::XMotion::Fly(){
TRACE("24EnteringCSpaceship::XMotion::Fly/n");//第24步
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
TRACE("25this=%p,pThis=%p/n",this,pThis);//第25步
TRACE("26m_nPosition=%d/n",pThis->m_nPosition);//第26步
TRACE("27m_nAcceleration=%d/n",pThis->m_nAcceleration);//第27步
}
int&CSpaceship::XMotion::GetPosition(){
TRACE("28EnteringCSpaceship::XMotion::GetPosition/n");//第28步
METHOD_PROLOGUE(CSpaceship,Motion)//makespThis
TRACE("29this=%p,pThis=%p/n",this,pThis);//第29步
TRACE("30m_nPosition=%d/n",pThis->m_nPosition);//第30步
TRACE("31m_nAcceleration=%d/n",pThis->m_nAcceleration);//第31步
returnpThis->m_nPosition;
}
BOOLCSpaceship::XVisual::QueryInterface(intnIid,void**ppvObj){
TRACE("EnteringCSpaceship::XVisual::QueryInterface--nIid=%d/n",nIid);
METHOD_PROLOGUE(CSpaceship,Visual)//makespThis
returnpThis->ExternalQueryInterface(nIid,ppvObj);//delegateto
//CSpaceship
}
DWORDCSpaceship::XVisual::Release(){
TRACE("43EnteringCSpaceship::XVisual::Release/n");//第43步
METHOD_PROLOGUE(CSpaceship,Visual)//makespThis
returnpThis->ExternalRelease();//delegatetoCSimulatedCmdTarget
}
DWORDCSpaceship::XVisual::AddRef(){
TRACE("EnteringCSpaceship::XVisual::AddRef/n");
METHOD_PROLOGUE(CSpaceship,Visual)//makespThis
returnpThis->ExternalAddRef();//delegatetoCSimulatedCmdTarget
}
voidCSpaceship::XVisual::Display(){
TRACE("33EnteringCSpaceship::XVisual::Display/n");//第33步
METHOD_PROLOGUE(CSpaceship,Visual)//makespThis
TRACE("34this=%p,pThis=%p/n",this,pThis);//第34步
TRACE("35m_nPosition=%d/n",pThis->m_nPosition);//第35步
TRACE("36m_nColor=%d/n",pThis->m_nColor);//第36步
}
//----------simulatesCOMcomponent----------------------------------
//InrealCOM,thiswouldbeDllGetClassObject,whichwouldbecalled
//wheneveraclientcalledCoGetClassObject
BOOLGetClassObject(intnClsid,intnIid,void**ppvObj)
{
ASSERT(nClsid==CLSID_CSpaceship);
ASSERT((nIid==IID_IUnknown)||(nIid==IID_IClassFactory));
returng_factory.ExternalQueryInterface(nIid,ppvObj);
//refcountis2,whichpreventsaccidentaldeletion
}