I have a situation where I have several layers of a component (which is a DragAndDropTarget). Not all of the layers are interested in all drop sources, but I noticed that it is only the top layer that gets asked the isInterestedInDragSource question. If I answer “false” I’d expect the rest of the DragAndDropTarget beneath (in z-order) to be asked, but this does not happen.
Should I work-around this, or is this perhaps not the way it was meant to be?
Another problem with my application: I have component A (which is a DragAndDropTarget), and a component B which is a child component of A (occupying the same area). If I set setInterceptsMouseClicks(false, true) on component B, component A stops receiving isInterestedInDragSource notifications in a drag/drop operation. This seems odd to me. Intuitively, all components in z-order should be queried…
Hmm - you’re right, it should recursively ask the parent comps if they’re interested. How about this tweak to juce_DragAndDropContainer.cpp:
[code] DragAndDropTarget* findTarget (const int screenX, const int screenY,
int& relX, int& relY)
{
Component* hit = getParentComponent();
if (hit == 0)
{
hit = Desktop::getInstance().findComponentAt (screenX, screenY);
}
else
{
int rx = screenX, ry = screenY;
hit->globalPositionToRelative (rx, ry);
hit = hit->getComponentAt (rx, ry);
}
while (hit != 0)
{
DragAndDropTarget* const ddt = dynamic_cast <DragAndDropTarget*> (hit);
if (ddt != 0)
{
relX = screenX;
relY = screenY;
hit->globalPositionToRelative (relX, relY);
if (ddt->isInterestedInDragSource (dragDesc))
return ddt;
}
hit = hit->getParentComponent();
}
return 0;
}[/code]
It does use the normal hit-testing mechanism to decide which component the mouse is over, so if you’ve turned off mouse interception, that comp wouldn’t be able to get dropped-on. It has to work this way in case there are funny-shaped components with odd hit-test regions.
I guess that is better, however have not tested it yet. But it still won’t handle situations where sibling components are overlapped (and deriving from DragAndDropTarget). What would be nice is a Component function that returns a set of Components which all intersect a point at x, y then use that set in the findTarget function. I know it might be tricky since more than one DDT might be interested. Maybe set a jassert for that?
Continuing on the “efficiency” note, since the findTarget method will report a DDT that is interested in the drag source, the calls to isInterestedInSource could be omitted in updateLocation. Though this would exclude more advanced DDTs that would allow drag/drop in a certain location within it… :?
Yeah, I have a few comps that use location-based testing to see if it’s interested, so that’d break stuff. It’s not really worth optimising anyway, I’d have thought.