punker76/gong-wpf-dragdrop

Drag Adorner Gets Clipped

osicka opened this issue · 1 comments

If you drag the adorner to the left or right of the screen the adorner gets clipped, which is bad if you need to look at the information in the adorner. (I have changing information based on what element you are over).

To fix this I make the adorner position relative to the position on the adorned element, in the middle it is in the centre, as you move left or right the adorner slowly shifts away from centre so that it is always fully visible.

To achieve this I modified DragDrog.cs.

In DropTarget_PreviewDragOver when setting the DragAdorner position

if (DontClipAdorner == true)
{
    _adornerPos.Offset((_adornerSize.Width * (tempAdornerPos.X / DragAdorner.AdornedElement.DesiredSize.Width * -1)), (_adornerSize.Height * -0.9));
}
else
{
    // When there is a custom adorner move to above the cursor and center it
    if (m_DragInfo != null && GetDragAdornerTemplate(m_DragInfo.VisualSource) != null)
        _adornerPos.Offset((_adornerSize.Width * -0.5), (_adornerSize.Height * -0.9));
    else
        _adornerPos.Offset(0, (_adornerSize.Height * -0.5));
}

and lower down when setting the EffectAdorner position

if (DontClipAdorner == true)                
{
    // Fixed the flickering adorner - Size changes to zero 'randomly'...?
    if (EffectAdorner.RenderSize.Width > 0 && EffectAdorner.RenderSize.Height > 0)
        _effectAdornerSize = EffectAdorner.RenderSize;

    adornerPos.Offset((_effectAdornerSize.Width * (adornerPos.X / EffectAdorner.AdornedElement.DesiredSize.Width * -1)), 25);
}
else
{
    adornerPos.Offset(20, 20);
}

this will be fixed in 0.1.3.9 but with this solution at DropTarget_PreviewDragOver

if (m_DragInfo != null) {
  // move the adorner
  var offsetX = _adornerSize.Width * -GetDragMouseAnchorPoint(m_DragInfo.VisualSource).X;
  var offsetY = _adornerSize.Height * -GetDragMouseAnchorPoint(m_DragInfo.VisualSource).Y;
  _adornerPos.Offset(offsetX, offsetY);
  var maxAdornerPosX = DragAdorner.AdornedElement.RenderSize.Width;
  var adornerPosRightX = (_adornerPos.X + _adornerSize.Width);
  if (adornerPosRightX > maxAdornerPosX) {
    _adornerPos.Offset(-adornerPosRightX + maxAdornerPosX, 0);
  }
}