📄 defaulthandler.c
字号:
HRESULT hr;
FIXME("(%p): semi-stub\n", pbc);
/* already running? if so nothing to do */
if (This->pOleDelegate)
return S_OK;
hr = CoCreateInstance(&This->clsid, NULL, CLSCTX_LOCAL_SERVER,
&IID_IOleObject, (void **)&This->pOleDelegate);
if (FAILED(hr))
return hr;
hr = IOleObject_Advise(This->pOleDelegate,
(IAdviseSink *)&This->lpvtblIAdviseSink,
&This->dwAdvConn);
if (SUCCEEDED(hr) && This->clientSite)
hr = IOleObject_SetClientSite(This->pOleDelegate, This->clientSite);
if (SUCCEEDED(hr))
{
IOleObject_QueryInterface(This->pOleDelegate, &IID_IPersistStorage,
(void **)&This->pPSDelegate);
if (This->pPSDelegate)
hr = IPersistStorage_InitNew(This->pPSDelegate, NULL);
}
if (SUCCEEDED(hr) && This->containerApp)
hr = IOleObject_SetHostNames(This->pOleDelegate, This->containerApp,
This->containerObj);
/* FIXME: do more stuff here:
* - IOleObject_GetMiscStatus
* - IOleObject_GetMoniker
* - IOleCache_OnRun
*/
if (SUCCEEDED(hr))
hr = IOleObject_QueryInterface(This->pOleDelegate, &IID_IDataObject,
(void **)&This->pDataDelegate);
if (SUCCEEDED(hr) && This->dataAdviseHolder)
hr = DataAdviseHolder_OnConnect(This->dataAdviseHolder, This->pDataDelegate);
if (FAILED(hr))
DefaultHandler_Stop(This);
return hr;
}
/************************************************************************
* DefaultHandler_IsRunning (IRunnableObject)
*
* See Windows documentation for more details on IRunnableObject methods.
*/
static BOOL WINAPI DefaultHandler_IsRunning(
IRunnableObject* iface)
{
DefaultHandler *This = impl_from_IRunnableObject(iface);
TRACE("()\n");
if (This->pOleDelegate)
return TRUE;
else
return FALSE;
}
/************************************************************************
* DefaultHandler_LockRunning (IRunnableObject)
*
* See Windows documentation for more details on IRunnableObject methods.
*/
static HRESULT WINAPI DefaultHandler_LockRunning(
IRunnableObject* iface,
BOOL fLock,
BOOL fLastUnlockCloses)
{
FIXME("()\n");
return S_OK;
}
/************************************************************************
* DefaultHandler_SetContainedObject (IRunnableObject)
*
* See Windows documentation for more details on IRunnableObject methods.
*/
static HRESULT WINAPI DefaultHandler_SetContainedObject(
IRunnableObject* iface,
BOOL fContained)
{
FIXME("()\n");
return S_OK;
}
static HRESULT WINAPI DefaultHandler_IAdviseSink_QueryInterface(
IAdviseSink *iface,
REFIID riid,
void **ppvObject)
{
if (IsEqualIID(riid, &IID_IUnknown) ||
IsEqualIID(riid, &IID_IAdviseSink))
{
*ppvObject = iface;
IAdviseSink_AddRef(iface);
return S_OK;
}
return E_NOINTERFACE;
}
static ULONG WINAPI DefaultHandler_IAdviseSink_AddRef(
IAdviseSink *iface)
{
DefaultHandler *This = impl_from_IAdviseSink(iface);
return IUnknown_AddRef((IUnknown *)&This->lpvtblIUnknown);
}
static ULONG WINAPI DefaultHandler_IAdviseSink_Release(
IAdviseSink *iface)
{
DefaultHandler *This = impl_from_IAdviseSink(iface);
return IUnknown_Release((IUnknown *)&This->lpvtblIUnknown);
}
static void WINAPI DefaultHandler_IAdviseSink_OnDataChange(
IAdviseSink *iface,
FORMATETC *pFormatetc,
STGMEDIUM *pStgmed)
{
FIXME(": stub\n");
}
static void WINAPI DefaultHandler_IAdviseSink_OnViewChange(
IAdviseSink *iface,
DWORD dwAspect,
LONG lindex)
{
FIXME(": stub\n");
}
static void WINAPI DefaultHandler_IAdviseSink_OnRename(
IAdviseSink *iface,
IMoniker *pmk)
{
DefaultHandler *This = impl_from_IAdviseSink(iface);
TRACE("(%p)\n", pmk);
if (This->oleAdviseHolder)
IOleAdviseHolder_SendOnRename(This->oleAdviseHolder, pmk);
}
static void WINAPI DefaultHandler_IAdviseSink_OnSave(
IAdviseSink *iface)
{
DefaultHandler *This = impl_from_IAdviseSink(iface);
TRACE("()\n");
if (This->oleAdviseHolder)
IOleAdviseHolder_SendOnSave(This->oleAdviseHolder);
}
static void WINAPI DefaultHandler_IAdviseSink_OnClose(
IAdviseSink *iface)
{
DefaultHandler *This = impl_from_IAdviseSink(iface);
TRACE("()\n");
if (This->oleAdviseHolder)
IOleAdviseHolder_SendOnClose(This->oleAdviseHolder);
DefaultHandler_Stop(This);
}
/*
* Virtual function tables for the DefaultHandler class.
*/
static const IOleObjectVtbl DefaultHandler_IOleObject_VTable =
{
DefaultHandler_QueryInterface,
DefaultHandler_AddRef,
DefaultHandler_Release,
DefaultHandler_SetClientSite,
DefaultHandler_GetClientSite,
DefaultHandler_SetHostNames,
DefaultHandler_Close,
DefaultHandler_SetMoniker,
DefaultHandler_GetMoniker,
DefaultHandler_InitFromData,
DefaultHandler_GetClipboardData,
DefaultHandler_DoVerb,
DefaultHandler_EnumVerbs,
DefaultHandler_Update,
DefaultHandler_IsUpToDate,
DefaultHandler_GetUserClassID,
DefaultHandler_GetUserType,
DefaultHandler_SetExtent,
DefaultHandler_GetExtent,
DefaultHandler_Advise,
DefaultHandler_Unadvise,
DefaultHandler_EnumAdvise,
DefaultHandler_GetMiscStatus,
DefaultHandler_SetColorScheme
};
static const IUnknownVtbl DefaultHandler_NDIUnknown_VTable =
{
DefaultHandler_NDIUnknown_QueryInterface,
DefaultHandler_NDIUnknown_AddRef,
DefaultHandler_NDIUnknown_Release,
};
static const IDataObjectVtbl DefaultHandler_IDataObject_VTable =
{
DefaultHandler_IDataObject_QueryInterface,
DefaultHandler_IDataObject_AddRef,
DefaultHandler_IDataObject_Release,
DefaultHandler_GetData,
DefaultHandler_GetDataHere,
DefaultHandler_QueryGetData,
DefaultHandler_GetCanonicalFormatEtc,
DefaultHandler_SetData,
DefaultHandler_EnumFormatEtc,
DefaultHandler_DAdvise,
DefaultHandler_DUnadvise,
DefaultHandler_EnumDAdvise
};
static const IRunnableObjectVtbl DefaultHandler_IRunnableObject_VTable =
{
DefaultHandler_IRunnableObject_QueryInterface,
DefaultHandler_IRunnableObject_AddRef,
DefaultHandler_IRunnableObject_Release,
DefaultHandler_GetRunningClass,
DefaultHandler_Run,
DefaultHandler_IsRunning,
DefaultHandler_LockRunning,
DefaultHandler_SetContainedObject
};
static const IAdviseSinkVtbl DefaultHandler_IAdviseSink_VTable =
{
DefaultHandler_IAdviseSink_QueryInterface,
DefaultHandler_IAdviseSink_AddRef,
DefaultHandler_IAdviseSink_Release,
DefaultHandler_IAdviseSink_OnDataChange,
DefaultHandler_IAdviseSink_OnViewChange,
DefaultHandler_IAdviseSink_OnRename,
DefaultHandler_IAdviseSink_OnSave,
DefaultHandler_IAdviseSink_OnClose
};
/*********************************************************
* Methods implementation for the DefaultHandler class.
*/
static DefaultHandler* DefaultHandler_Construct(
REFCLSID clsid,
LPUNKNOWN pUnkOuter)
{
DefaultHandler* This = NULL;
/*
* Allocate space for the object.
*/
This = HeapAlloc(GetProcessHeap(), 0, sizeof(DefaultHandler));
if (!This)
return This;
This->lpVtbl = &DefaultHandler_IOleObject_VTable;
This->lpvtblIUnknown = &DefaultHandler_NDIUnknown_VTable;
This->lpvtblIDataObject = &DefaultHandler_IDataObject_VTable;
This->lpvtblIRunnableObject = &DefaultHandler_IRunnableObject_VTable;
This->lpvtblIAdviseSink = &DefaultHandler_IAdviseSink_VTable;
/*
* Start with one reference count. The caller of this function
* must release the interface pointer when it is done.
*/
This->ref = 1;
/*
* Initialize the outer unknown
* We don't keep a reference on the outer unknown since, the way
* aggregation works, our lifetime is at least as large as it's
* lifetime.
*/
if (!pUnkOuter)
pUnkOuter = (IUnknown*)&This->lpvtblIUnknown;
This->outerUnknown = pUnkOuter;
/*
* Create a datacache object.
* We aggregate with the datacache. Make sure we pass our outer
* unknown as the datacache's outer unknown.
*/
CreateDataCache(This->outerUnknown,
clsid,
&IID_IUnknown,
(void**)&This->dataCache);
/*
* Initialize the other data members of the class.
*/
memcpy(&This->clsid, clsid, sizeof(CLSID));
This->clientSite = NULL;
This->oleAdviseHolder = NULL;
This->dataAdviseHolder = NULL;
This->containerApp = NULL;
This->containerObj = NULL;
This->pOleDelegate = NULL;
This->pPSDelegate = NULL;
This->pDataDelegate = NULL;
This->dwAdvConn = 0;
return This;
}
static void DefaultHandler_Destroy(
DefaultHandler* This)
{
/* release delegates */
DefaultHandler_Stop(This);
/* Free the strings idenfitying the object */
HeapFree( GetProcessHeap(), 0, This->containerApp );
This->containerApp = NULL;
HeapFree( GetProcessHeap(), 0, This->containerObj );
This->containerObj = NULL;
/* Release our reference to the data cache. */
if (This->dataCache)
{
IUnknown_Release(This->dataCache);
This->dataCache = NULL;
}
/* Same thing for the client site. */
if (This->clientSite)
{
IOleClientSite_Release(This->clientSite);
This->clientSite = NULL;
}
/* And the advise holder. */
if (This->oleAdviseHolder)
{
IOleAdviseHolder_Release(This->oleAdviseHolder);
This->oleAdviseHolder = NULL;
}
/* And the data advise holder. */
if (This->dataAdviseHolder)
{
IDataAdviseHolder_Release(This->dataAdviseHolder);
This->dataAdviseHolder = NULL;
}
/* Free the actual default handler structure. */
HeapFree(GetProcessHeap(), 0, This);
}
/******************************************************************************
* OleCreateDefaultHandler [OLE32.@]
*/
HRESULT WINAPI OleCreateDefaultHandler(
REFCLSID clsid,
LPUNKNOWN pUnkOuter,
REFIID riid,
LPVOID* ppvObj)
{
DefaultHandler* newHandler = NULL;
HRESULT hr = S_OK;
TRACE("(%s, %p, %s, %p)\n", debugstr_guid(clsid), pUnkOuter, debugstr_guid(riid), ppvObj);
/*
* Sanity check
*/
if (!ppvObj)
return E_POINTER;
*ppvObj = NULL;
/*
* If This handler is constructed for aggregation, make sure
* the caller is requesting the IUnknown interface.
* This is necessary because it's the only time the non-delegating
* IUnknown pointer can be returned to the outside.
*/
if (pUnkOuter && !IsEqualIID(&IID_IUnknown, riid))
return CLASS_E_NOAGGREGATION;
/*
* Try to construct a new instance of the class.
*/
newHandler = DefaultHandler_Construct(clsid, pUnkOuter);
if (!newHandler)
return E_OUTOFMEMORY;
/*
* Make sure it supports the interface required by the caller.
*/
hr = IUnknown_QueryInterface((IUnknown*)&newHandler->lpvtblIUnknown, riid, ppvObj);
/*
* Release the reference obtained in the constructor. If
* the QueryInterface was unsuccessful, it will free the class.
*/
IUnknown_Release((IUnknown*)&newHandler->lpvtblIUnknown);
return hr;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -