// DDShellExt.cpp : Implementation of CDDShellExt #include "tchar.h" #include "DDShellExt.h" #include "ClientCatchcopy.h" #include extern HINSTANCE g_hInst; extern long g_cDllRef; CDDShellExt::CDDShellExt(): m_cRef(1) { InterlockedIncrement(&g_cDllRef); } CDDShellExt::~CDDShellExt() { InterlockedDecrement(&g_cDllRef); } // Query to the interface the component supported. IFACEMETHODIMP CDDShellExt::QueryInterface(REFIID riid, void **ppv) { if(riid == IID_IUnknown || riid == IID_IContextMenu) { *ppv = static_cast(this); } else if (riid == IID_IShellExtInit) { *ppv = static_cast(this); } else { *ppv = NULL; return E_NOINTERFACE; } reinterpret_cast(*ppv)->AddRef(); return S_OK; } // Increase the reference count for an interface on an object. IFACEMETHODIMP_(ULONG) CDDShellExt::AddRef() { return InterlockedIncrement(&m_cRef); } // Decrease the reference count for an interface on an object. IFACEMETHODIMP_(ULONG) CDDShellExt::Release() { ULONG cRef = InterlockedDecrement(&m_cRef); if (0 == cRef) delete this; return cRef; } STDMETHODIMP CDDShellExt::Initialize(LPCITEMIDLIST pidlFolder,LPDATAOBJECT pDO,HKEY hProgID) { (void)hProgID; if(!connected) { bool b = m_ac.connectToServer(); if (b==true) { connected=true; } else return E_FAIL; } FORMATETC fmt={CF_HDROP,NULL,DVASPECT_CONTENT,-1,TYMED_HGLOBAL}; STGMEDIUM stg={TYMED_HGLOBAL}; HDROP hDrop; fDestDir[0]=0; if (!SHGetPathFromIDList(pidlFolder,fDestDir)) { #ifdef CATCHCOPY_EXPLORER_PLUGIN_DEBUG MessageBox(NULL,L"Initialize",L"E_FAIL 1",MB_OK); #endif // CATCHCOPY_EXPLORER_PLUGIN_DEBUG return E_FAIL; } // Detect if it's explorer that started the operation by enumerating available // clipboard formats and searching for one that only explorer uses IEnumFORMATETC *en; FORMATETC fmt2; WCHAR fmtName[65535]=L"\0"; fFromExplorer=false; pDO->EnumFormatEtc(DATADIR_GET,&en); while(en->Next(1,&fmt2,NULL)==S_OK){ GetClipboardFormatName(fmt2.cfFormat,fmtName,sizeof(fmtName)); if (!wcscmp(fmtName,CFSTR_SHELLIDLIST)) fFromExplorer=true; } en->Release(); // Look for CF_HDROP data in the data object. If there // is no such data, return an error back to Explorer. if (FAILED(pDO->GetData(&fmt,&stg))) { #ifdef CATCHCOPY_EXPLORER_PLUGIN_DEBUG MessageBox(NULL,L"Initialize",L"E_INVALIDARG 2",MB_OK); #endif // CATCHCOPY_EXPLORER_PLUGIN_DEBUG return E_INVALIDARG; } // Get a pointer to the actual data. hDrop=(HDROP)GlobalLock(stg.hGlobal); // Make sure it worked. if (hDrop==NULL) { #ifdef CATCHCOPY_EXPLORER_PLUGIN_DEBUG MessageBox(NULL,L"Initialize",L"E_INVALIDARG 1",MB_OK); #endif // CATCHCOPY_EXPLORER_PLUGIN_DEBUG return E_INVALIDARG; } UINT numFiles,i; WCHAR fn[MAX_PATH]=L""; numFiles=DragQueryFile(hDrop,0xFFFFFFFF,NULL,0); if (numFiles) { for(i=0;ilpVerb)) return E_INVALIDARG; switch(LOWORD(pInfo->lpVerb)) { case 0:// copy if(!m_ac.addCopyWithDestination(sources,fDestDir)) return E_FAIL; break; case 1:// move if(!m_ac.addMoveWithDestination(sources,fDestDir)) return E_FAIL; break; default : return S_OK; } return S_OK; }