MSDN中 WINOLEAPI RegisterDragDrop( HWND hwnd, //Handle to a window that can accept drops IDropTarget * pDropTarget //Pointer to object that is to be target of drop ); hwnd [in] Handle to a window that can be a target for an OLE drag-and-drop operation. pDropTarget [in] Pointer to the IDropTarget interface on the object that is to be the target of a drag-and-drop operation in a specified window. This interface is used to communicate OLE drag-and-drop information for that window.
我是让框架接受拖拽,其它部分与上面一样,可是就是框架就是不接受 class CMainFrame : public CFrameWindowImpl<CMainFrame>, public IDropTargetImpl<CMainFrame>, public CUpdateUI<CMainFrame>, public CMessageFilter, public CIdleHandler
http://www.vckbase.com/document/viewdoc/?id=258
然后向系统注册拖拽的窗口句柄,RegisterDragDrop(...)
当有拖拽Data 进入到你的窗口时调用 DragEnter 方法,你可以查询 拖拽Data 所支持的数据格式,
对于IE链结拖动,他的 格式名称是 UniformResourceLocator, 下面的代码是取url 的过程:
p 就是链结urlDragEnter(IDataObject *pDataObject, DWORD grfKeyState, POINTL pt, DWORD *pdwEffect)
{
IEnumFORMATETC* p=NULL;
pDataObject->EnumFormatEtc(DATADIR_GET,&p);
FORMATETC pFormat[20];
ZeroMemory(&(pFormat[0]),20*sizeof(FORMATETC));
ULONG uFetched=0;
p->Next(20,&(pFormat[0]),&uFetched);
TCHAR szFormatName[MAX_PATH];
for(int i=0;i<uFetched;i++)
{
GetClipboardFormatName(pFormat[i].cfFormat,szFormatName,MAX_PATH);
if(StrCmp(szFormatName,"UniformResourceLocator")==0)
{
FORMATETC urlFe={pFormat[i].cfFormat,NULL,DVASPECT_CONTENT,-1,TYMED_HGLOBAL};
STGMEDIUM stg;
if(FAILED(pDataObject->GetData(&urlFe,&stg)))
{
MessageBox(NULL,"Uniform Resource Locator Get Data Failure!","Get Data",MB_OK); }
else
{
switch(stg.tymed)
{
case TYMED_HGLOBAL:
{
char* p=(char*)GlobalLock(stg.hGlobal);
MessageBox(NULL,p,"URL",MB_OK);
if(stg.pUnkForRelease==NULL)
{
GlobalFree(stg.hGlobal);
}
}
break;
default:
}
ReleaseStgMedium(&stg);
}
}
}
}
谢谢!
class CShowInfoWnd :
public CScrollWindowImpl<CShowInfoWnd>,
public IDropTargetImpl<CShowInfoWnd>
{
BEGIN_MSG_MAP(CShowInfoWnd)
MESSAGE_HANDLER(WM_ERASEBKGND, OnEraseBkgnd)
CHAIN_MSG_MAP(IDropTargetImpl<CShowInfoWnd>)
CHAIN_MSG_MAP(CScrollWindowImpl<CShowInfoWnd>)
MESSAGE_HANDLER(WM_SIZE,OnSize)
END_MSG_MAP()
HRESULT OnDrop (IDataObject * pDataObject, DWORD grfKeyState, POINTL pt, DWORD * pdwEffect)
{
if(!IsDragToSameWnd())
{
string yourLinker;
GetTextData(m_yourLinker,pDataObject);
}
return S_OK;
}
};
//IDropTarget½Ó¿ÚʵÀý,¸ÃʵÀýÓÉ´°¿Ú¶ÔÏó¼Ì³Ð,²»»áÓɽӿڵÄReleaseÊͷŸöÔÏó,´°¿ÚÏûÃðʱIDropTarget²»¿ÉÓÃ
template <class T>
class ATL_NO_VTABLE IDropTargetImpl :
public IDropTarget,
public CMessageMap
{
public:
BEGIN_MSG_MAP(IDropTargetImpl)
MESSAGE_HANDLER(WM_CREATE,OnCreate)
MESSAGE_HANDLER(WM_DESTROY,OnDestory)
END_MSG_MAP() LRESULT OnCreate(UINT /*uMsg*/, WPARAM wParam, LPARAM /*lParam*/, BOOL& bHandled)
{
T* pT = static_cast<T*>(this);
IDropTarget *pDropTarget;
QueryInterface(IID_IDropTarget,(void **)&pDropTarget);
CoLockObjectExternal(pDropTarget, TRUE, FALSE); //Ëø¶¨¸Ã¶ÔÏóʹËüÒ»Ö±ÔÚÄÚ´æÖÐ
RegisterDragDrop(pT->m_hWnd, pDropTarget); //ʹ¸Ã´°¿Ú¿ÉÒÔ½ÓÊÕÍж¯
bHandled=FALSE;
return S_OK;
}
LRESULT OnDestory(UINT /*uMsg*/, WPARAM wParam, LPARAM /*lParam*/, BOOL& bHandled)
{
T* pT = static_cast<T*>(this);
RevokeDragDrop(pT->m_hWnd); //È¡Ïû´°¿Ú¿ÉÒÔ½ÓÊÕÍж¯µÄÄÜÁ¦
IDropTarget *pDropTarget;
QueryInterface(IID_IDropTarget,(void **)&pDropTarget);
HRESULT hr=CoLockObjectExternal(pDropTarget, FALSE, TRUE); //È¡Ïû¶ÔÏóËø¶¨
bHandled=FALSE;
return S_OK;
} //IUnknown implementation
HRESULT __stdcall QueryInterface (REFIID iid, void ** ppvObject)
{
if(iid == IID_IDropTarget || iid == IID_IUnknown)
{
AddRef();
*ppvObject = this;
return S_OK;
}
else
{
*ppvObject = 0;
return E_NOINTERFACE;
}
}
ULONG __stdcall AddRef (void){return 1;}
ULONG __stdcall Release (void){return 1;}
//»Øµ÷º¯Êý
//pdwEffect ÊôÐÔ˵Ã÷
// DROPEFFECT_NONE = ÎÞÍж¯ÓÐЧÐÔ
// DROPEFFECT_COPY = Ϊ¿½±´ÑùʽµÄÍж¯
// DROPEFFECT_MOVE = ΪÒƶ¯ÑùʽµÄÍж¯
// µ±Íж¯½øÈë¸Ã´°¿Úʱ(Êý¾ÝÍж¯½ø´°¿Úʱ,Åжϴ°¿ÚÊÇ·ñÖ§³Ö¸ÃÊý¾Ý,Èç¹û²»Ö§³ÖÉèÖÃ*pdwEffect=DROPEFFECT_NONE)
HRESULT OnDragEnter(IDataObject * pDataObject, DWORD grfKeyState, POINTL pt, DWORD *pdwEffect)
{
return S_OK;
}
HRESULT OnDragOver (DWORD grfKeyState, POINTL pt, DWORD * pdwEffect)
{
return S_OK;
}
HRESULT OnDragLeave()
{
return S_OK;
}
HRESULT OnDrop (IDataObject * pDataObject, DWORD grfKeyState, POINTL pt, DWORD * pdwEffect)
{
return S_OK;
}
// IDropTarget implementation
HRESULT __stdcall DragEnter (IDataObject * pDataObject, DWORD grfKeyState, POINTL pt, DWORD * pdwEffect)
{
T* pT = static_cast<T*>(this);
return pT->OnDragEnter(pDataObject, grfKeyState, pt, pdwEffect);
}
HRESULT __stdcall DragOver (DWORD grfKeyState, POINTL pt, DWORD * pdwEffect)
{
T* pT = static_cast<T*>(this);
return pT->OnDragOver (grfKeyState, pt, pdwEffect);
}
HRESULT __stdcall DragLeave (void)
{
T* pT = static_cast<T*>(this);
pT->OnDragLeave ();
return S_OK;
}
HRESULT __stdcall Drop (IDataObject * pDataObject, DWORD grfKeyState, POINTL pt, DWORD * pdwEffect)
{
T* pT = static_cast<T*>(this);
return pT->OnDrop (pDataObject,grfKeyState, pt, pdwEffect);
}
//¸¨Öú·½·¨
public:
DWORD DropEffect(DWORD grfKeyState, POINTL pt, DWORD dwAllowed)
{
DWORD dwEffect = 0;
// 1. check "pt" -> do we allow a drop at the specified coordinates?
// 2. work out that the drop-effect should be based on grfKeyState
if(grfKeyState & MK_CONTROL)
{
dwEffect = dwAllowed & DROPEFFECT_COPY;
}
else if(grfKeyState & MK_SHIFT)
{
dwEffect = dwAllowed & DROPEFFECT_MOVE;
} // 3. no key-modifiers were specified (or drop effect not allowed), so
// base the effect on those allowed by the dropsource
if(dwEffect == 0)
{
if(dwAllowed & DROPEFFECT_COPY) dwEffect = DROPEFFECT_COPY;
if(dwAllowed & DROPEFFECT_MOVE) dwEffect = DROPEFFECT_MOVE;
}
return dwEffect;
}
// QueryDataObject private helper routine
BOOL QueryDataObject(FORMATETC &fmtetc,IDataObject *pDataObject)
{
return pDataObject->QueryGetData(&fmtetc) == S_OK ? TRUE : FALSE;
}
BOOL GetTextData(string &text,IDataObject *pDataObject)
{
FORMATETC fmtetc = { CF_TEXT, 0, DVASPECT_CONTENT, -1, TYMED_HGLOBAL }; //CF_TEXT¸ñʽ
STGMEDIUM stgmed;
BOOL isRight=FALSE;
if(pDataObject->QueryGetData(&fmtetc) == S_OK)
{
if(pDataObject->GetData(&fmtetc, &stgmed) == S_OK)
{
LPVOID data = GlobalLock(stgmed.hGlobal);
text=(char *)data;
GlobalUnlock(stgmed.hGlobal);
ReleaseStgMedium(&stgmed);// release the data using the COM API
isRight=TRUE;
}
}
return isRight;
}
};
1.由于托动目标和窗口对应,所以在你要接收托动的窗口增加托动目标的支持
public IDropTargetImpl<CShowInfoWnd>
2.在该窗口的消息处理映射宏中增加
CHAIN_MSG_MAP(IDropTargetImpl<CShowInfoWnd>)
由IDropTargetImpl自动完成托动目标的初始化和释放操作,也就是你说的注册不不是(这不要你作)
3.增加托动消息处理函数,由IDropTargetImpl中回调,当有信息托动到该窗口时自动回调到它这个虚函数
HRESULT OnDrop (IDataObject * pDataObject, DWORD grfKeyState, POINTL pt, DWORD *pdwEffect)
{
if(!IsDragToSameWnd()) //判断是否托动源和目标是同一个窗口
{
string yourLinker; //如果托动的是连接,那你的连接放在这个字符串中
GetTextData(m_yourLinker,pDataObject); //这是IDropTargetImpl支持,它获取剪切板为文本类型的信息
}
return S_OK;
}
就这样就完成你的要求了
IDropTargetImpl在上面的文章中以有了你拷贝下来就可以了中间的;Í些是在拷贝时中文的乱码问题不要求可以了
WINOLEAPI RegisterDragDrop(
HWND hwnd, //Handle to a window that can accept drops
IDropTarget * pDropTarget //Pointer to object that is to be target of drop
);
hwnd [in] Handle to a window that can be a target for an OLE drag-and-drop operation. pDropTarget [in] Pointer to the IDropTarget interface on the object that is to be the target of a drag-and-drop operation in a specified window. This interface is used to communicate OLE drag-and-drop information for that window.
class CMainFrame : public CFrameWindowImpl<CMainFrame>,
public IDropTargetImpl<CMainFrame>,
public CUpdateUI<CMainFrame>,
public CMessageFilter,
public CIdleHandler
CHAIN_MSG_MAP(IDropTargetImpl<CMainFrame>)没有
还是就是你的
WM_CREATE 中的消息处理函数中Handle 要为FALSE
或放到CHAIN_MSG_MAP(IDropTargetImpl<CMainFrame>)的第行
#include "DropTarget.h" //DropTarget.hb 是你贴出的内容
class CMainFrame : public CFrameWindowImpl<CMainFrame>,
public IDropTargetImpl<CMainFrame>,
public CUpdateUI<CMainFrame>,
public CMessageFilter,
public CIdleHandler
{
public:
DECLARE_FRAME_WND_CLASS(NULL, IDR_MAINFRAME) CTuotuTestView m_view;
CCommandBarCtrl m_CmdBar; virtual BOOL PreTranslateMessage(MSG* pMsg);
virtual BOOL OnIdle();
BEGIN_UPDATE_UI_MAP(CMainFrame)
UPDATE_ELEMENT(ID_VIEW_TOOLBAR, UPDUI_MENUPOPUP)
UPDATE_ELEMENT(ID_VIEW_STATUS_BAR, UPDUI_MENUPOPUP)
END_UPDATE_UI_MAP() BEGIN_MSG_MAP(CMainFrame)
MESSAGE_HANDLER(WM_CREATE, OnCreate)
COMMAND_ID_HANDLER(ID_APP_EXIT, OnFileExit)
COMMAND_ID_HANDLER(ID_FILE_NEW, OnFileNew)
COMMAND_ID_HANDLER(ID_VIEW_TOOLBAR, OnViewToolBar)
COMMAND_ID_HANDLER(ID_VIEW_STATUS_BAR, OnViewStatusBar)
COMMAND_ID_HANDLER(ID_APP_ABOUT, OnAppAbout)
MESSAGE_HANDLER(WM_DROPFILES, OnDropFiles)
CHAIN_MSG_MAP(CUpdateUI<CMainFrame>)
CHAIN_MSG_MAP(CFrameWindowImpl<CMainFrame>)
CHAIN_MSG_MAP(IDropTargetImpl<CMainFrame>)
END_MSG_MAP()
HRESULT OnDrop (IDataObject * pDataObject, DWORD grfKeyState, POINTL pt, DWORD * pdwEffect)
{
//if(!IsDragToSameWnd())
{
string yourLinker;
GetTextData(yourLinker,pDataObject);
//GetTextData(yourLinker,pDataObject);
::MessageBox(NULL,yourLinker.c_str(),"",0);
}
return S_OK;
} LRESULT CMainFrame::OnCreate(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, BOOL& /*bHandled*/)
{
......
RegisterDragDrop(m_hWnd,this);
return 0;
} .....
}
2.
BEGIN_MSG_MAP(CMainFrame)
CHAIN_MSG_MAP(IDropTargetImpl<CMainFrame>)发在第一行
...
END_MSG_MAP()
或
LRESULT CMainFrame::OnCreate(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, BOOL& bHandled)
{
...
bHandled=FALSE;
return 0;
}3.你的OnCreate中RegisterDragDrop(m_hWnd,this);不要
LRESULT CMainFrame::OnCreate(UINT /*uMsg*/, WPARAM /*wParam*/, LPARAM /*lParam*/, BOOL& /*bHandled*/)
{
......
return 0;
}
int WINAPI _tWinMain(HINSTANCE hInstance, HINSTANCE /*hPrevInstance*/, LPTSTR lpstrCmdLine, int nCmdShow)
{
HRESULT hRes = ::CoInitialize(NULL);
hRes=::OleInitialize(NULL);
.........
.........
::CoUninitialize();
::OleUninitialize();
return nRet;
}