/// <summary> /// If is grid enabled, snap to intersects /// </summary> private void SnapToGrid() { if (_canvas.IsGridEnabled) { int cellWidth = DesignerCanvas.GridCellWidth; var selected = _canvas.SelectedTables.ToArray(); double topConnectionLimit = double.MaxValue; double bottomConnectionLimit = double.MaxValue; double leftConnectionLimit = double.MaxValue; double rightConnectionLimit = double.MaxValue; foreach (TableContent item in _canvas.SelectedTables) { foreach (ConnectionInfoViewModel model in _connections.Where(t => t.SourceViewModel.Equals(item.TableViewModel))) { ConnectionInfoViewModel.GetConnectionLimits(ref topConnectionLimit, ref bottomConnectionLimit, ref leftConnectionLimit, ref rightConnectionLimit, model.SourceConnector, model); } foreach (ConnectionInfoViewModel model in _connections.Where(t => t.DestinationViewModel.Equals(item.TableViewModel))) { ConnectionInfoViewModel.GetConnectionLimits(ref topConnectionLimit, ref bottomConnectionLimit, ref leftConnectionLimit, ref rightConnectionLimit, model.DestinationConnector, model); } } foreach (TableContent item in selected) { double top = item.TableViewModel.Top; double left = item.TableViewModel.Left; double bottom = top + item.TableViewModel.Height; double right = left + item.TableViewModel.Width; double approxCellTop = Math.Round(top / cellWidth, MidpointRounding.AwayFromZero) * cellWidth; double approxCellLeft = Math.Round(left / cellWidth, MidpointRounding.AwayFromZero) * cellWidth; if (WillSnapToGridBrokeConnections(topConnectionLimit, leftConnectionLimit, bottomConnectionLimit, rightConnectionLimit, top, left, bottom, right, approxCellTop, approxCellLeft)) { continue; } DesignerCanvas.SetLeft(item, approxCellLeft); DesignerCanvas.SetTop(item, approxCellTop); item.TableViewModel.Left = approxCellLeft; item.TableViewModel.Top = approxCellTop; } } }
/// <summary> /// If is grid enabled, snap to intersects /// </summary> private void SnapToGrid() { if (_canvas.IsGridEnabled) { double topConnectionLimit = double.MaxValue; double bottomConnectionLimit = double.MaxValue; double leftConnectionLimit = double.MaxValue; double rightConnectionLimit = double.MaxValue; foreach (ConnectionInfoViewModel model in _connections.Where(t => t.SourceViewModel.Equals(_item.TableViewModel))) { ConnectionInfoViewModel.GetConnectionLimits(ref topConnectionLimit, ref bottomConnectionLimit, ref leftConnectionLimit, ref rightConnectionLimit, model.SourceConnector, model); } foreach (ConnectionInfoViewModel model in _connections.Where(t => t.DestinationViewModel.Equals(_item.TableViewModel))) { ConnectionInfoViewModel.GetConnectionLimits(ref topConnectionLimit, ref bottomConnectionLimit, ref leftConnectionLimit, ref rightConnectionLimit, model.DestinationConnector, model); } double top = _item.TableViewModel.Top; double left = _item.TableViewModel.Left; double bottom = top + _item.TableViewModel.Height; double right = left + _item.TableViewModel.Width; int cellWidth = DesignerCanvas.GridCellWidth; double approxCell; switch (VerticalAlignment) { case VerticalAlignment.Top: approxCell = Math.Round(top / cellWidth, MidpointRounding.AwayFromZero) * cellWidth; if (topConnectionLimit < double.MaxValue) { if (approxCell > top - topConnectionLimit) { DesignerCanvas.SetTop(_item, approxCell); _item.TableViewModel.Top = approxCell; } } else { DesignerCanvas.SetTop(_item, approxCell); _item.TableViewModel.Top = approxCell; } break; case VerticalAlignment.Bottom: approxCell = Math.Round(bottom / cellWidth, MidpointRounding.AwayFromZero) * cellWidth; if (bottomConnectionLimit < double.MaxValue) { if (approxCell < bottom + bottomConnectionLimit) { _item.TableViewModel.Height = approxCell - _item.TableViewModel.Top; _item.Height = _item.TableViewModel.Height; } } else { _item.TableViewModel.Height = approxCell - _item.TableViewModel.Top; _item.Height = _item.TableViewModel.Height; } break; } switch (HorizontalAlignment) { case HorizontalAlignment.Left: approxCell = Math.Round(left / cellWidth, MidpointRounding.AwayFromZero) * cellWidth; if (leftConnectionLimit < double.MaxValue) { if (approxCell > left - leftConnectionLimit) { DesignerCanvas.SetLeft(_item, approxCell); _item.TableViewModel.Left = approxCell; } } else { DesignerCanvas.SetLeft(_item, approxCell); _item.TableViewModel.Left = approxCell; } break; case HorizontalAlignment.Right: approxCell = Math.Round(right / cellWidth, MidpointRounding.AwayFromZero) * cellWidth; if (rightConnectionLimit < double.MaxValue) { if (approxCell < right + rightConnectionLimit) { _item.TableViewModel.Width = approxCell - _item.TableViewModel.Left; _item.Width = _item.TableViewModel.Width; } } else { _item.TableViewModel.Width = approxCell - _item.TableViewModel.Left; _item.Width = _item.TableViewModel.Width; } break; } } }
/// <summary> /// Drag of thumb in progress /// </summary> /// <param name="sender"></param> /// <param name="e"></param> private void ResizeThumb_DragDelta(object sender, DragDeltaEventArgs e) { if (_item != null && _canvas != null && _item.IsSelected) { double maxDeltaVertical = _canvas.ActualHeight - (DesignerCanvas.GetTop(_item) + _item.ActualHeight); double maxDeltaHorizontal = _canvas.ActualWidth - (DesignerCanvas.GetLeft(_item) + _item.ActualWidth); var minDeltaVertical = _item.ActualHeight - _item.MinHeight; var minDeltaHorizontal = _item.ActualWidth - _item.MinWidth; #region Bad approach //Bad approach //foreach(TableContent item in _canvas.SelectedTables) //{ // minLeft = Math.Min(DesignerCanvas.GetLeft(item), minLeft); // minTop = Math.Min(DesignerCanvas.GetTop(item), minTop); // maxLeft = Math.Max(DesignerCanvas.GetLeft(item) + item.ActualWidth, maxLeft); // maxTop = Math.Max(DesignerCanvas.GetTop(item) + item.ActualHeight, maxTop); // if (item.TableViewModel.ViewMode != TableViewMode.NameOnly) // { // minDeltaVertical = Math.Min(item.ActualHeight - item.MinHeight, minDeltaVertical); // } // minDeltaHorizontal = Math.Min(item.ActualWidth - item.MinWidth, minDeltaHorizontal); // maxDeltaVertical = Math.Min(_canvas.ActualHeight - (DesignerCanvas.GetTop(item) + item.ActualHeight), maxDeltaVertical); // maxDeltaHorizontal = Math.Min(_canvas.ActualWidth - (DesignerCanvas.GetLeft(item) + item.ActualWidth), maxDeltaHorizontal); //} #endregion double topConnectionLimit = double.MaxValue; double bottomConnectionLimit = double.MaxValue; double leftConnectionLimit = double.MaxValue; double rightConnectionLimit = double.MaxValue; foreach (ConnectionInfoViewModel model in _connections.Where(t => t.SourceViewModel.Equals(_item.TableViewModel))) { ConnectionInfoViewModel.GetConnectionLimits(ref topConnectionLimit, ref bottomConnectionLimit, ref leftConnectionLimit, ref rightConnectionLimit, model.SourceConnector, model); } foreach (ConnectionInfoViewModel model in _connections.Where(t => t.DestinationViewModel.Equals(_item.TableViewModel))) { ConnectionInfoViewModel.GetConnectionLimits(ref topConnectionLimit, ref bottomConnectionLimit, ref leftConnectionLimit, ref rightConnectionLimit, model.DestinationConnector, model); } if (_item.TableViewModel.ViewMode != TableViewMode.NameOnly) { double deltaVertical; switch (VerticalAlignment) { case VerticalAlignment.Bottom: deltaVertical = e.VerticalChange > 0 && e.VerticalChange >= maxDeltaVertical ? 0 : Math.Min(-e.VerticalChange, minDeltaVertical); if (bottomConnectionLimit < double.MaxValue) { if (DesignerCanvas.GetTop(_item) + _item.ActualHeight - deltaVertical >= (DesignerCanvas.GetTop(_item) + _item.ActualHeight) + bottomConnectionLimit) { deltaVertical = 0; } } _item.Height = _item.ActualHeight - (int)deltaVertical; _item.TableViewModel.Height = _item.Height; break; case VerticalAlignment.Top: deltaVertical = (int)Math.Min(Math.Max(-DesignerCanvas.GetTop(_item), e.VerticalChange), minDeltaVertical); if (topConnectionLimit < double.MaxValue) { if (deltaVertical < 0 && DesignerCanvas.GetTop(_item) + deltaVertical <= DesignerCanvas.GetTop(_item) - topConnectionLimit) { deltaVertical = 0; } } var topPos = DesignerCanvas.GetTop(_item) + deltaVertical; DesignerCanvas.SetTop(_item, topPos); _item.Height = _item.ActualHeight - deltaVertical; _item.TableViewModel.Height = _item.Height; _item.TableViewModel.Top = topPos; break; } } double deltaHorizontal; switch (HorizontalAlignment) { case HorizontalAlignment.Left: deltaHorizontal = (int)Math.Min(Math.Max(-DesignerCanvas.GetLeft(_item), e.HorizontalChange), minDeltaHorizontal); if (leftConnectionLimit < double.MaxValue) { if (deltaHorizontal < 0 && DesignerCanvas.GetLeft(_item) + deltaHorizontal <= DesignerCanvas.GetLeft(_item) - leftConnectionLimit) { deltaHorizontal = 0; } } var leftPos = DesignerCanvas.GetLeft(_item) + deltaHorizontal; DesignerCanvas.SetLeft(_item, leftPos); _item.Width = _item.ActualWidth - deltaHorizontal; _item.TableViewModel.Width = _item.Width; _item.TableViewModel.Left = leftPos; break; case HorizontalAlignment.Right: deltaHorizontal = e.HorizontalChange > 0 && e.HorizontalChange >= maxDeltaHorizontal ? 0 : (int)Math.Min(-e.HorizontalChange, minDeltaHorizontal); if (rightConnectionLimit < double.MaxValue) { if (DesignerCanvas.GetLeft(_item) + _item.ActualWidth - deltaHorizontal >= DesignerCanvas.GetLeft(_item) + _item.ActualWidth + rightConnectionLimit) { deltaHorizontal = 0; } } _item.Width = _item.ActualWidth - deltaHorizontal; _item.TableViewModel.Width = _item.Width; break; } } e.Handled = true; }
/// <summary> /// Mouse drag in progress /// </summary> /// <param name="sender"></param> /// <param name="dragDeltaEventArgs"></param> private void OnDragDelta(object sender, DragDeltaEventArgs dragDeltaEventArgs) { if (_item != null && _canvas != null && _item.IsSelected) { double minLeft = double.MaxValue; double minTop = double.MaxValue; double maxTop = double.MinValue; double maxLeft = double.MinValue; foreach (TableContent item in _canvas.SelectedTables) { minLeft = Math.Min(DesignerCanvas.GetLeft(item), minLeft); minTop = Math.Min(DesignerCanvas.GetTop(item), minTop); maxLeft = Math.Max(DesignerCanvas.GetLeft(item) + item.ActualWidth, maxLeft); maxTop = Math.Max(DesignerCanvas.GetTop(item) + item.ActualHeight, maxTop); } double deltaHorizontal = (int)Math.Max(-minLeft, dragDeltaEventArgs.HorizontalChange); double deltaVertical = (int)Math.Max(-minTop, dragDeltaEventArgs.VerticalChange); //Limit movement by connection position double topConnectionLimit = double.MaxValue; double bottomConnectionLimit = double.MaxValue; double leftConnectionLimit = double.MaxValue; double rightConnectionLimit = double.MaxValue; foreach (TableContent item in _canvas.SelectedTables) { foreach (ConnectionInfoViewModel model in _connections.Where(t => t.SourceViewModel.Equals(item.TableViewModel))) { ConnectionInfoViewModel.GetConnectionLimits(ref topConnectionLimit, ref bottomConnectionLimit, ref leftConnectionLimit, ref rightConnectionLimit, model.SourceConnector, model); } foreach (ConnectionInfoViewModel model in _connections.Where(t => t.DestinationViewModel.Equals(item.TableViewModel))) { ConnectionInfoViewModel.GetConnectionLimits(ref topConnectionLimit, ref bottomConnectionLimit, ref leftConnectionLimit, ref rightConnectionLimit, model.DestinationConnector, model); } } if (_item.TableViewModel.AreLimitsEnabled) { if (topConnectionLimit < double.MaxValue) { if (deltaVertical < 0 && minTop + deltaVertical <= minTop - topConnectionLimit) { deltaVertical = 0; } } if (bottomConnectionLimit < double.MaxValue) { if (deltaVertical > 0 && maxTop + deltaVertical >= maxTop + bottomConnectionLimit) { deltaVertical = 0; } } if (leftConnectionLimit < double.MaxValue) { if (deltaHorizontal < 0 && minLeft + deltaHorizontal <= minLeft - leftConnectionLimit) { deltaHorizontal = 0; } } if (rightConnectionLimit < double.MaxValue) { if (deltaHorizontal > 0 && maxLeft + deltaHorizontal >= maxLeft + rightConnectionLimit) { deltaHorizontal = 0; } } if (maxLeft >= _canvas.ActualWidth && dragDeltaEventArgs.HorizontalChange > 0) { deltaHorizontal = 0; } if (maxTop >= _canvas.ActualHeight && dragDeltaEventArgs.VerticalChange > 0) { deltaVertical = 0; } } var selected = _canvas.SelectedTables.ToArray(); foreach (TableContent item in selected) { var leftPos = DesignerCanvas.GetLeft(item) + deltaHorizontal; var topPos = DesignerCanvas.GetTop(item) + deltaVertical; DesignerCanvas.SetLeft(item, leftPos); DesignerCanvas.SetTop(item, topPos); item.TableViewModel.Left = leftPos; item.TableViewModel.Top = topPos; } dragDeltaEventArgs.Handled = true; } }