void DoDragSelectMouseMove(DTkViewer dv, DPoint pt) { // rectangular area to update with paint event DRect updateRect = new DRect(); // initial update rect updateRect = figureHandler.SelectionFigure.Rect; // drag select figure figureHandler.SelectionFigure.TopLeft = dragPt; figureHandler.SelectionFigure.BottomRight = pt; if (figureHandler.SelectionFigure.Width < 0) { figureHandler.SelectionFigure.X += figureHandler.SelectionFigure.Width; figureHandler.SelectionFigure.Width = -figureHandler.SelectionFigure.Width; } if (figureHandler.SelectionFigure.Height < 0) { figureHandler.SelectionFigure.Y += figureHandler.SelectionFigure.Height; figureHandler.SelectionFigure.Height = -figureHandler.SelectionFigure.Height; } // final update rect updateRect = updateRect.Union(figureHandler.SelectionFigure.Rect); // update drawing dv.Update(updateRect); }
void ErasePolylines(DPoint eraserPt, IList<Figure> figures, ref DRect updateRect, GroupFigure parent) { for (int i = figures.Count - 1; i >= 0; i--) if (figures[i] is PolylinebaseFigure) { PolylinebaseFigure f = (PolylinebaseFigure)figures[i]; DPoint rotPt = f.TransformPointToFigure(eraserPt); DPoints ptsToRemove = new DPoints(); if (f.Points != null) foreach (DPoint pt in f.Points) if (DGeom.PointInCircle(pt, rotPt, figureHandler.EraserFigure.Size / 2)) ptsToRemove.Add(pt); if (ptsToRemove.Count > 0) { // add polyline figure bounding box to updateRect updateRect = updateRect.Union(GetBoundingBox(f)); if (parent != null) { // remove child figure and account for rect changes DRect oldR = parent.Rect; ErasePolyline(ptsToRemove, f, parent); DRect newR = parent.Rect; DGeom.UpdateRotationPosition(f, oldR, newR); } else ErasePolyline(ptsToRemove, f, parent); } } else if (figures[i] is GroupFigure) { GroupFigure f = (GroupFigure)figures[i]; // recurse into group figure and also update rotation position DRect oldR = f.Rect; ErasePolylines(f.TransformPointToFigure(eraserPt), f.ChildFigures, ref updateRect, f); DRect newR = f.Rect; DGeom.UpdateRotationPosition(f, oldR, newR); // clean up group figure if no longer needed if (f.ChildFigures.Count == 1) figureHandler.UngroupFigure(f); else if (f.ChildFigures.Count < 1) figures.Remove(f); } }
void DoDragFigureMouseMove(DTkViewer dv, DPoint pt) { // rectangular area to update with paint event DRect updateRect = new DRect(); // move selected figures switch (mouseHitTest) { case DHitTest.Body: System.Diagnostics.Trace.Assert(currentFigure != null, "currentFigure is null"); // drag figure event if (DragFigureEvt != null) DragFigureEvt(null, currentFigure, dv.EngineToClient(pt)); // if figure drag op is cancelled then quit this function if (cancelledFigureDrag) { cancelledFigureDrag = false; return; } // bound pt to canvas BoundPtToPage(pt); // initial update rect updateRect = GetBoundingBox(currentFigure); foreach (Figure f in figureHandler.SelectedFigures) updateRect = updateRect.Union(GetBoundingBox(f)); // apply x/y delta to figures DPoint dPos = CalcDragDelta(pt); if (gridSnapPosition && grid > 0) { DPoint o = GridSnapOffset(currentFigure.X + dPos.X, currentFigure.Y + dPos.Y); dPos.X += o.X; dPos.Y += o.Y; pt.X += o.X; pt.Y += o.Y; } if (dPos.X != 0 || dPos.Y != 0) foreach (Figure f in figureHandler.SelectedFigures) if (!f.Locked) { f.X += dPos.X; f.Y += dPos.Y; } // store drag pt for reference later (eg. next mousemove event) dragPt = pt; // final update rect foreach (Figure f in figureHandler.SelectedFigures) updateRect = updateRect.Union(GetBoundingBox(f)); break; case DHitTest.SelectRect: goto case DHitTest.Body; case DHitTest.Resize: System.Diagnostics.Trace.Assert(currentFigure != null, "currentFigure is null"); // bound pt to canvas BoundPtToPage(pt); // alert figure we are going to resize it currentFigure.BeforeResize(); // inital update rect updateRect = GetBoundingBox(currentFigure); // translate point onto the same rotated plane as the figure pt = currentFigure.RotatePointToFigure(pt); // apply width/height delta to figure DPoint dSize = CalcSizeDelta(pt, currentFigure, LockingAspectRatio || currentFigure.LockAspectRatio); if (lockInitialAspectRatio && !(figureLockAspectRatioMode == DHsmLockAspectRatioMode.Always || currentFigure.LockAspectRatio)) { DPoint dSizeUnlocked = CalcSizeDelta(pt, currentFigure, false); if (figureLockAspectRatioMode == DHsmLockAspectRatioMode.Never || Math.Abs(dSizeUnlocked.X - dSize.X) >= unlockInitalAspectRatioThreshold || Math.Abs(dSizeUnlocked.Y - dSize.Y) >= unlockInitalAspectRatioThreshold) { lockInitialAspectRatio = false; dSize = dSizeUnlocked; } } if (currentFigure.Width > 0 && currentFigure.Width + dSize.X < currentFigure.MinSize) { dSize.X = currentFigure.MinSize - currentFigure.Width; if (LockingAspectRatio || currentFigure.LockAspectRatio) dSize.Y = (currentFigure.Height / currentFigure.Width) * dSize.X; } if (currentFigure.Height > 0 && currentFigure.Height + dSize.Y < currentFigure.MinSize) { dSize.Y = currentFigure.MinSize - currentFigure.Height; if (LockingAspectRatio || currentFigure.LockAspectRatio) dSize.X = (currentFigure.Width / currentFigure.Height) * dSize.Y; } DRect oldRect = currentFigure.Rect; currentFigure.Width += dSize.X; currentFigure.Height += dSize.Y; // snap resize if (gridSnapResize && grid > 0) { DPoint o2 = GridSnapOffset(currentFigure.Width, currentFigure.Height); currentFigure.Width += o2.X; currentFigure.Height += o2.Y; } DGeom.UpdateRotationPosition(currentFigure, oldRect, currentFigure.Rect); // final update rect updateRect = updateRect.Union(GetBoundingBox(currentFigure)); // alert figure we have finished resizing currentFigure.AfterResize(); // debug message #if DEBUG DoDebugMessage(string.Format("{0} {1}", dSize.X, dSize.Y)); #endif break; case DHitTest.RepositionPoint: System.Diagnostics.Trace.Assert(currentFigure != null, "currentFigure is null"); // bound pt to canvas BoundPtToPage(pt); // inital update rect updateRect = GetBoundingBox(currentFigure); // get our reposition point interface IRepositionPoint rp = (IRepositionPoint)currentFigure; // setup points DPoint newPoint; newPoint = new DPoint(pt.X, pt.Y); SetPointDelegate setPoint = delegate(DPoint point) { // snap point to grid if (gridSnapLines && grid > 0) { DPoint o3 = GridSnapOffset(point.X, point.Y); point.X += o3.X; point.Y += o3.Y; } // now set point rp.RepositionPoint = point; }; GetRotationalSnapDelegate getRotationalSnap = delegate(double angleRemainder) { if (angleRemainder < figureSnapRange) return -angleRemainder; else if (angleRemainder > figureSnapAngle - figureSnapRange) return figureSnapAngle - angleRemainder; else return 0; }; if (rp.AnglePoint != null) { // find the current angle of the line and the remainder when divided by the snap angle double currentAngle = DGeom.AngleBetweenPoints(rp.RepositionPoint, rp.AnglePoint); double ar = currentAngle % figureSnapAngle; // reposition line double newAngle; switch (FigureSnapAngleMode) { case DHsmSnapAngleMode.Always: // slide point along snap angle newAngle = DGeom.AngleBetweenPoints(newPoint, rp.AnglePoint); ar = newAngle % figureSnapAngle; if (ar < figureSnapAngle / 2) setPoint(DGeom.RotatePoint(newPoint, rp.AnglePoint, -ar)); else setPoint(DGeom.RotatePoint(newPoint, rp.AnglePoint, figureSnapAngle - ar)); break; case DHsmSnapAngleMode.Default: if (ar == 0) { // line is snapped, test if new angle will unsnap the line newAngle = DGeom.AngleBetweenPoints(newPoint, rp.AnglePoint); ar = newAngle % figureSnapAngle; if (ar > figureSnapRange && ar < figureSnapAngle - figureSnapRange) // unsnapped, set new point setPoint(newPoint); else { // slide point along snap angle newPoint = DGeom.RotatePoint(newPoint, rp.AnglePoint, getRotationalSnap(ar)); setPoint(newPoint); } } else { // set new point setPoint(newPoint); // test whether to snap our line newAngle = DGeom.AngleBetweenPoints(newPoint, rp.AnglePoint); ar = newAngle % figureSnapAngle; double rotationalSnap = getRotationalSnap(ar); // snap it if (rotationalSnap != 0) setPoint(DGeom.RotatePoint(newPoint, rp.AnglePoint, rotationalSnap)); } break; case DHsmSnapAngleMode.Never: // set new point setPoint(newPoint); break; } } else setPoint(newPoint); // final update rect updateRect = updateRect.Union(GetBoundingBox(currentFigure)); break; case DHitTest.Rotate: System.Diagnostics.Trace.Assert(currentFigure != null, "currentFigure is null"); // initial update rect updateRect = GetBoundingBox(currentFigure); // apply rotation to figure double newRot = GetRotationOfPointComparedToFigure(currentFigure, pt) - dragRot; double r = newRot % figureSnapAngle; switch (figureSnapAngleMode) { case DHsmSnapAngleMode.Always: if (r < figureSnapAngle / 2) currentFigure.Rotation = newRot - r; else currentFigure.Rotation = newRot + figureSnapAngle - r; break; case DHsmSnapAngleMode.Default: if (r < figureSnapRange) currentFigure.Rotation = newRot - r; else if (r > figureSnapAngle - figureSnapRange) currentFigure.Rotation = newRot + figureSnapAngle - r; else currentFigure.Rotation = newRot; break; case DHsmSnapAngleMode.Never: currentFigure.Rotation = newRot; break; } // final update rect updateRect = updateRect.Union(GetBoundingBox(currentFigure)); #if DEBUG // debug message DoDebugMessage((currentFigure.Rotation * 180 / Math.PI).ToString()); #endif break; } // update drawing dv.Update(updateRect); }
public DRect BoundingRect(IList<Figure> figs) { DRect r = new DRect(0, 0, 0, 0); if (figs.Count == 1) { r = figs[0].Rect; foreach (Figure f in figs) r = r.Union(f.Rect); } else if (figs.Count > 1) { r = DGeom.BoundingBoxOfRotatedRect(figs[0].Rect, figs[0].Rotation); foreach (Figure f in figs) r = r.Union(DGeom.BoundingBoxOfRotatedRect(f.Rect, f.Rotation)); } return r; }