Click here to Skip to main content
15,883,606 members
Please Sign up or sign in to vote.
1.00/5 (1 vote)
See more:
My question is related to the aspect of drag and drop in MFC programming.

I know there are four classes (COleDataSource,COleDataObject,COleDropTarget and COleDropSource)which can realize the function of drag and drop. Data sources (as implemented by COleDataSource objects) represent the source side of the data transfer. Data objects (as implemented by COleDataObject objects) represent the destination side of the data transfer.The COleDropTarget provides the communication mechanism between a window and the OLE libraries.To get a window to accept drop commands, you should first create an object of the COleDropTarget class, and then call the Register function with a pointer to the desired CWnd object as the only parameter.
The COleDropTarget class handles the receiving portion of the drag-and-drop operation. The COleDropSource object is responsible for determining when a drag operation begins, providing feedback during the drag operation, and determining when the drag operation ends.

The drop effects are like this:
DROPEFFECT_NONE: Drop target cannot accept the data. Corresponding cursor is
DROPEFFECT_COPY: Drop results in a copy. The original data is untouched by the drag source. Corresponding cursor is
DROPEFFECT_MOVE: Drag source should remove the data. Corresponding cursor is
DROPEFFECT_LINK: The data will be "linked to" by the drop target. Corresponding cursor is

These cursors are not displayed. But i am sure you know them also.These cursors are default cursors when drop and drop.

Now i want to change them with my own cursors. I can change these default cursors through the COleDropSource::GiveFeedback() function. The specification of the function is described in MSDN.

Here is the part of my codes to change the default cursor.

1.override the class of COleDropSource and the related function
//override the class
class CDropSource: public COleDropSource
{
public:
	CDropSource();       

	// Overrides
	SCODE GiveFeedback(DROPEFFECT dropEffect);
	virtual SCODE QueryContinueDrag(BOOL bEscapePressed, DWORD dwKeyState);
	virtual BOOL OnBeginDrag(CWnd* pWnd);
};

//override the function of GiveFeedback to change these default cursors
SCODE CDropSource::GiveFeedback(DROPEFFECT dropEffect)
{
//change the default cursor corresponding to drop effect
//the new cursor can be either the other system cursors or the cursors //that user define

	ASSERT_VALID(this);

	switch(dropEffect)
	{
	case DROPEFFECT_NONE:
        //change the default cursor corresponding to DROPEFFECT_NONE
		SetCursor(LoadCursor(NULL,IDC_NO));
		break;

	case DROPEFFECT_MOVE:
        //change the default cursor corresponding to DROPEFFECT_MOVE
		SetCursor(LoadCursor(NULL,IDC_NO));
		break;

	case DROPEFFECT_COPY:
        //change the default cursor corresponding to DROPEFFECT_COPY
		SetCursor(LoadCursor(NULL,IDC_NO));
		break;

	case DROPEFFECT_LINK:
        //change the default cursor corresponding to DROPEFFECT_LINK
                SetCursor(AfxGetApp()->LoadCursor(IDC_DRAGSRC));
		break;

	case DROPEFFECT_SCROLL:
        //change the default cursor corresponding to DROPEFFECT_SCROLL
		SetCursor(LoadCursor(NULL,IDC_NO));
		break;
	}

	return S_OK;

	// don't change the cursor until drag is officially started
	return m_bDragStarted ? DRAGDROP_S_USEDEFAULTCURSORS : S_OK;
}

2.pass the member of CDropSource to the COleDataSource::DoDragDrop function when beginning drag
//begin drag
CDropSource m_DropSource;
COleDataSource source;
source.CacheGlobalData(m_nformat, hData );
source.DoDragDrop(DROPEFFECT_LINK,NULL,&m_DropSource);
GlobalFree( hData );
//end drag


Now the question is here. There are two situations.
First,if the window is registered as the COleDropTarget window,then changing default cursor in CDropSource::GiveFeedback function is in effect and the four default cursors are can be changed.
Second, if the window is not registered as the COleDropTarget window, then the parameter value of dropEffect in GiveFeedback function is DROPEFFECT_NONE. And now the default cursor can not be changed, the SetCursor function is of no effect.


And how can i change the default cursor in the second situation?


My english is bad, i wish you can understand my meaning above. Thanks very much.



The question has been uploaded for one days,but there has no answer for the question. I believe that there must be somebody who can resolve this simple question. I really need your help. Thanks a lot.

I updated the format of your question to make it "readable".
-E,G.-
Posted
Updated 1-May-11 20:01pm
v4

I guess :-O ,
it does not lie in the MFC Drag&Drop philosophy
to allow the "not registered" windows (for example CSplitterWnd)
to change the drag cursor inside of Source::DoDrag() loop... :)
 
Share this answer
 
Hi !!..

I am stuck in the same problem. First of all , I thank the solution contributor !!! I am bit confused about previous solution. Could please clarify that the DoDrag method is member of CDropSource or COleDataSource ?. I checked both class's member functions, I couldnt find out DoDrag(). Expecting your valuable suggestions.

Thanks
 
Share this answer
 
v2
For soluton 1, I can't understand your meaning. Of cause the DoDrag() method is not the member of COleDateSource. I guess, if you want to talk about DoDragDrop method?

Tanks skaprakash.
 
Share this answer
 

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

  Print Answers RSS


CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900