|
|
/*++
shmenu.cpp
this is for IShellMenu and related stuff. eventually all of the fsmenu.c functionality should be in here
--*/
class CFMDropTarget : public IDropTarget { public:
CFMDropTarget(); ~CFMDropTarget();
HRESULT Init ( HWND hwnd, IShellFolder *psf, LPITEMIDLIST pidl, DWORD dwFlags);
// IUnknown methods
virtual STDMETHODIMP QueryInterface(REFIID riid, PVOID *ppvObj); virtual STDMETHODIMP_(ULONG) AddRef(void); virtual STDMETHODIMP_(ULONG) Release(void);
STDMETHODIMP DragEnter( IDataObject *pdata, DWORD grfKeyState, POINTL pt, DWORD *pdwEffect) {return _pdrop->DragEnter(pdata, grfKeyState, pt, pdwEffect);} STDMETHODIMP DragOver( DWORD grfKeyState, POINTL pt, DWORD *pdwEffect) {return _pdrop->DragOver(grfKeyState, pt, pdwEffect);} STDMETHODIMP DragLeave( void) {return _pdrop->DragLeave();} STDMETHODIMP Drop( IDataObject *pDataObj, DWORD grfKeyState, POINTL pt, DWORD *pdwEffect) {return _pdrop->Drop(pDataObj, grfKeyState, pt, pdwEffect);}
private:
ULONG _cRef; IShellFolder *_psf; // the psf to use...
LPITEMIDLIST _pidl; DWORD _dwFlags; IDropTarget *_pdrop; // the actual droptarget
}
CFMDropTarget :: CFMDropTarget () { _cRef = 1; DllAddRef(); }
CFMDropTarget :: ~CFMDropTarget () { SAFERELEASE(_psf); if(pidl) ILFree(pidl); SAFERELEASE(_pdrop); DllRelease(); }
HRESULT CFMDropTarget :: QueryInterface(REFIID riid, PVOID *ppvObj) { HRESULT hr = E_NOINTERFACE;
*ppvObj = NULL;
if (IsEqualIID(riid, IID_IUnknown) || IsEqualIID(riid, IID_IDropTarget)) { AddRef(); *ppvObj = (LPVOID) SAFECAST(this, IDropTarget*); hr = S_OK;
}
return hr; }
ULONG CFMDropTarget :: AddRef(void) {
_cRef++;
return _cRef;
}
ULONG CFMDropTarget :: Release(void) { ASSERT (_cRef > 0);
cRef--;
if (!cRef) { //time to go bye bye
delete this; return 0; }
return cRef;
}
// FEATURE: ZEKEL we are just using the psf here...we need to support more
HRESULT Init ( HWND hwnd, IShellFolder *psf, LPITEMIDLIST pidl, DWORD dwFlags) { HRESULT hr = E_INVALIDARG;
if(psf) hr = psf->QueryInterface(IID_IShellFolder, (LPVOID *) &_psf);
_pidl = ILClone(pidl); _dwFlags = dwFlags;
if(SUCCEEDED(hr) && _psf && _pidl) { hr = _psf->CreateViewObject(hwnd, IID_IDropTarget, (LPVOID*) &_pdrop); }
return hr; }
//FEATURE: ZEKEL right now this doesnt support ordering, and assumes that you
//want to drop right onto the current menu. this is just a start.
//pidl and dwFlags are just dummy params
HRESULT CFMDropTarget_CreateAndInit( HWND hwnd, IShellFolder *psf, LPITEMIDLIST pidl, DWORD dwFlags, LPVOID *ppvObj) { HRESULT hr = E_OUTOFMEMORY; CFMDropTarget *pdt;
ASSERT(ppvObj) if(ppvObj) *ppvObj = NULL; else return E_INVALIDARG;
pdt = new CFMDropTargetNULL;
if (pdt) { hr = pdt->Init(hwnd, psf, pidl, dwFlags);
if (SUCCEEDED(hr)) *ppvObj= SAFECAST(pdt, IDropTarget * ); else pdt->Release(); } return hr; }
if (psf) {
hr = psf->QueryInterface(IID_IShellFolder, (LPVOID *) &psfMine);
if(SUCCEEDED(hr) && psfMine) {
}
#if 0 // ZEKEL
{ if(pmgoi->dwFlags & (MNGO_TOPGAP | MNGO_BOTTOMGAP)) { //then we need to use the current psf as the droptarget
// and the pidl is just a marker
} else { // we need to use the pidl's psf as the droptarget if possible
DWORD dwAttr = SFGAO_DROPTARGET; hr = psf->lpVtbl->GetAttributesOf(1, (LPCITEMIDLIST*)&pfmi->pidl, &dwAttr); if (SUCCEEDED(hres) && (dwAttr & SFGAO_DROPTARGET)) { hr = psf->lpVtbl->GetUIObjectOf(hwnd, 1, (LPCITEMIDLIST*)&pfmi->pidl, IID_IDropTarget, NULL, (LPVOID*)&_pdropgtCur); } } #endif
|