protected void DragCardCompleted() { // Release the card and its group foreach (Card c in DraggedCards) { c.ReleaseControl(); } Card.Group.ReleaseControl(); // Remove the visual feedback var mwc = _mainWin.Content as Visual; if (mwc != null) { AdornerLayer layer = AdornerLayer.GetAdornerLayer(mwc); foreach (CardDragAdorner overlay in OverlayElements) { layer.Remove(overlay); overlay.Dispose(); } } OverlayElements.Clear(); // Raise CardOutEvent if (_lastDragTarget != null) { _lastDragTarget.RaiseEvent(new CardsEventArgs(Card, DraggedCards, CardOutEvent, this)); _lastDragTarget = null; } // Raise CardDroppedEvent IInputElement res = Mouse.DirectlyOver; if (res != null) { var args = new CardsEventArgs(Card, DraggedCards, CardDroppedEvent, this) { MouseOffset = _mouseOffset, FaceUp = !(Keyboard.IsKeyDown(Key.LeftShift) || Keyboard.IsKeyDown(Key.RightShift)) }; res.RaiseEvent(args); } // Restore full opacity // FIX (jods): if the cards have been moved to another group, groupCtrl is null. // But in this case nothing has to be done opacity-wise since // the CardControls have been unloaded. GroupControl groupCtrl = GroupControl; if (groupCtrl != null) { foreach (CardControl cardCtrl in Selection.GetCardControls(groupCtrl, this)) { cardCtrl.Opacity = 1; } } DraggedCards.Clear(); }
protected void DragCardStarted() { DraggedCards.Clear(); // in theory draggedCards should already be empty, but it's better to recover if there was a problem during last DnD if (!Selection.IsEmpty()) { DraggedCards.AddRange(Selection.Cards); } else if (_isOverCount) { DraggedCards.AddRange(MultipleCards.Cast <Card>()); } else if (Card != null) { DraggedCards.Add(Card); } else { return; } // Fix: Card == null can occur, e.g. hold the mouse down but don't move, dismiss the card with a keyboard shortcut (e.g. Delete) and move the mouse after that (with the left button still down). _isDragging = true; // Keep control of the card and the group it's in foreach (Card c in DraggedCards) { c.KeepControl(); } Card.Group.KeepControl(); // Hides the card view RaiseEvent(new CardEventArgs(CardHoveredEvent, this)); // Starts the drag-and-drop ScaleFactor = TransformToAncestor(_mainWin).TransformBounds(new Rect(0, 0, 1, 1)).Size; //bool rot90 = (Card.Orientation & CardOrientation.Rot90) != 0; _mouseOffset = new Vector(_mousePt.X * Program.GameEngine.Definition.CardWidth / ActualWidth, _mousePt.Y * Program.GameEngine.Definition.CardHeight / ActualHeight); // Create adorners var mwn = _mainWin.Content as Visual; AdornerLayer layer = null; if (mwn != null) { layer = AdornerLayer.GetAdornerLayer(mwn); } double offset = 0; double step = ActualWidth * 1.05; // HACK: if the selected card is in HandControl, its ContentPresenter has a RenderTransform, // which we must account for if (GroupControl is HandControl) { var parent = VisualTreeHelper.GetParent(this) as ContentPresenter; if (parent != null) { step = 1.05 * parent.RenderTransform.TransformBounds(new Rect(0, 0, ActualWidth, 0)).Width; } } foreach (CardControl cardCtrl in Selection.GetCardControls(GroupControl, this)) { // Create an adorner if (Card.Group is Table) { var overlay = new CardDragAdorner(cardCtrl, _mouseOffset); OverlayElements.Add(overlay); if (layer != null) { layer.Add(overlay); } } else { // If there are multiple cards but they don't come from the table, // layout the adorners properly var overlay = new CardDragAdorner(this, cardCtrl, _mouseOffset); OverlayElements.Add(overlay); if (cardCtrl != this) { offset += step; overlay.OffsetBy(offset, 0); overlay.CollapseTo(0, 0, false); } if (layer != null) { layer.Add(overlay); } } // Make the card translucent cardCtrl.Opacity = 0.4; } if (!Selection.IsEmpty() || !_isOverCount) { return; } // Create additional fake adorners when dragging from the count label offset = 0; foreach (Card c in MultipleCards.Skip(1)) { offset += step; var overlay = new CardDragAdorner(this, _mouseOffset); overlay.OffsetBy(offset, 0); overlay.CollapseTo(0, 0, false); OverlayElements.Add(overlay); if (layer != null) { layer.Add(overlay); } } }