private static void LockToGrid(CanvasPixelPosition canvasOffset, [NotNull] TileCanvas target, ref double x, ref double y) { if (canvasOffset == null) { return; } var scale = 1.0 / target.CurrentZoom(); var grid = TileCanvas.GridSize * scale; var bias = (3 * grid) / 5.0; x = Math.Round((x + bias) / grid) * grid; x -= (canvasOffset.X * scale) % grid; y = Math.Round((y + bias) / grid) * grid; y -= (canvasOffset.Y * scale) % grid; }
/// <summary> /// Continue a pen stroke /// </summary> public void Stroke(PointerEventArgs penEvent, CanvasPixelPosition canvasOffset, [NotNull] TileCanvas target) { try { if (penEvent?.CurrentPoint?.Properties == null) { return; } var x = penEvent.CurrentPoint.Position.X; var y = penEvent.CurrentPoint.Position.Y; var isEraser = penEvent.CurrentPoint.Properties.IsEraser || penEvent.CurrentPoint.Properties.IsRightButtonPressed; // treat right-click as erase if (penEvent.KeyModifiers.HasFlag(VirtualKeyModifiers.Control)) { // hacky straight line tool: if (_stroke.Count > 1) { _stroke.RemoveAt(_stroke.Count - 1); // replace last point instead of adding a new one } } if (penEvent.KeyModifiers.HasFlag(VirtualKeyModifiers.Menu))// this is actually *ALT* { LockToGrid(canvasOffset, target, ref x, ref y); } _stroke.Add(new DPoint { X = x, Y = y, StylusId = GuessPointerId(penEvent.CurrentPoint), Pressure = penEvent.CurrentPoint.Properties.Pressure, IsErase = isEraser }); _renderTarget.Invalidate(); } catch (Exception ex) { Logging.WriteLogMessage(ex.ToString()); } }