diff --git a/Greenshot/Helpers/ScaleHelper.cs b/Greenshot/Helpers/ScaleHelper.cs
index 96840c509..bb1103ec1 100644
--- a/Greenshot/Helpers/ScaleHelper.cs
+++ b/Greenshot/Helpers/ScaleHelper.cs
@@ -227,92 +227,70 @@ namespace Greenshot.Helpers {
/// position of the handle/gripper being used for resized, see Position
/// coordinates of the used handle/gripper, adjusted coordinates will be written to this reference
private static void adjustCoordsForRationalScale(RectangleF originalRectangle, Positions resizeHandlePosition, ref PointF resizeHandleCoords) {
- float originalRatio = originalRectangle.Width / originalRectangle.Height;
- float newWidth, newHeight, newRatio;
- int flippedRatioSign;
+ SizeF selectedRectangle, newSize;
+
switch(resizeHandlePosition) {
case Positions.TopLeft:
- newWidth = originalRectangle.Right - resizeHandleCoords.X;
- newHeight = originalRectangle.Bottom - resizeHandleCoords.Y;
- newRatio = newWidth / newHeight;
- flippedRatioSign = Math.Sign(newRatio) * Math.Sign(originalRatio);
- if (Math.Abs(newRatio) > Math.Abs(originalRatio)) {
- // scaled rectangle (ratio) would be wider than original
- // keep height and tweak width to maintain aspect ratio
- float tweakedWidth = newHeight * originalRatio * flippedRatioSign;
- resizeHandleCoords.X = originalRectangle.Right - tweakedWidth;
- } else if(Math.Abs(newRatio) < Math.Abs(originalRatio)) {
- // scaled rectangle (ratio) would be taller than original
- // keep width and tweak height to maintain aspect ratio
- float tweakedHeight = newWidth / originalRatio * flippedRatioSign;
- resizeHandleCoords.Y = originalRectangle.Bottom - tweakedHeight;
- }
+ selectedRectangle = new SizeF(originalRectangle.Right - resizeHandleCoords.X, originalRectangle.Bottom - resizeHandleCoords.Y);
+ newSize = getNewSizeForRationalScale(originalRectangle.Size, selectedRectangle);
+ resizeHandleCoords.X = originalRectangle.Right - newSize.Width;
+ resizeHandleCoords.Y = originalRectangle.Bottom - newSize.Height;
break;
case Positions.TopRight:
- newWidth = resizeHandleCoords.X - originalRectangle.Left;
- newHeight = originalRectangle.Bottom - resizeHandleCoords.Y;
- newRatio = newWidth / newHeight;
- flippedRatioSign = Math.Sign(newRatio) * Math.Sign(originalRatio);
-
- if (Math.Abs(newRatio) > Math.Abs(originalRatio)) {
- // scaled rectangle (ratio) would be wider than original
- // keep height and tweak width to maintain aspect ratio
- float tweakedWidth = newHeight * originalRatio * flippedRatioSign;
- resizeHandleCoords.X = originalRectangle.Left + tweakedWidth;
- }
- else if (Math.Abs(newRatio) < Math.Abs(originalRatio)) {
- // scaled rectangle (ratio) would be taller than original
- // keep width and tweak height to maintain aspect ratio
- float tweakedHeight = newWidth / originalRatio * flippedRatioSign;
- resizeHandleCoords.Y = originalRectangle.Bottom - tweakedHeight;
- }
+ selectedRectangle = new SizeF(resizeHandleCoords.X - originalRectangle.Left, originalRectangle.Bottom - resizeHandleCoords.Y);
+ newSize = getNewSizeForRationalScale(originalRectangle.Size, selectedRectangle);
+ resizeHandleCoords.X = originalRectangle.Left + newSize.Width;
+ resizeHandleCoords.Y = originalRectangle.Bottom - newSize.Height;
break;
case Positions.BottomLeft:
- newWidth = originalRectangle.Right - resizeHandleCoords.X;
- newHeight = resizeHandleCoords.Y - originalRectangle.Top;
- newRatio = newWidth / newHeight;
- flippedRatioSign = Math.Sign(newRatio) * Math.Sign(originalRatio);
-
- if (Math.Abs(newRatio) > Math.Abs(originalRatio)) {
- // scaled rectangle (ratio) would be wider than original
- // keep height and tweak width to maintain aspect ratio
- float tweakedWidth = newHeight * originalRatio * flippedRatioSign;
- resizeHandleCoords.X = originalRectangle.Right - tweakedWidth;
- }
- else if (Math.Abs(newRatio) < Math.Abs(originalRatio)) {
- // scaled rectangle (ratio) would be taller than original
- // keep width and tweak height to maintain aspect ratio
- float tweakedHeight = newWidth / originalRatio * flippedRatioSign;
- resizeHandleCoords.Y = originalRectangle.Top + tweakedHeight;
- }
+ selectedRectangle = new SizeF(originalRectangle.Right - resizeHandleCoords.X, resizeHandleCoords.Y - originalRectangle.Top);
+ newSize = getNewSizeForRationalScale(originalRectangle.Size, selectedRectangle);
+ resizeHandleCoords.X = originalRectangle.Right - newSize.Width;
+ resizeHandleCoords.Y = originalRectangle.Top + newSize.Height;
break;
case Positions.BottomRight:
- newWidth = resizeHandleCoords.X - originalRectangle.Left;
- newHeight = resizeHandleCoords.Y - originalRectangle.Top;
- newRatio = newWidth / newHeight;
- flippedRatioSign = Math.Sign(newRatio) * Math.Sign(originalRatio);
-
- if (Math.Abs(newRatio) > Math.Abs(originalRatio)) {
- // scaled rectangle (ratio) would be wider than original
- // keep height and tweak width to maintain aspect ratio
- float tweakedWidth = newHeight * originalRatio * flippedRatioSign;
- resizeHandleCoords.X = originalRectangle.Left + tweakedWidth;
- }
- else if (Math.Abs(newRatio) < Math.Abs(originalRatio)) {
- // TODO this is the same code as else if for topleft!
- // scaled rectangle (ratio) would be taller than original
- // keep width and tweak height to maintain aspect ratio
- float tweakedHeight = newWidth / originalRatio * flippedRatioSign;
- resizeHandleCoords.Y = originalRectangle.Top + tweakedHeight;
- }
+ selectedRectangle = new SizeF(resizeHandleCoords.X - originalRectangle.Left, resizeHandleCoords.Y - originalRectangle.Top);
+ newSize = getNewSizeForRationalScale(originalRectangle.Size, selectedRectangle);
+ resizeHandleCoords.X = originalRectangle.Left + newSize.Width;
+ resizeHandleCoords.Y = originalRectangle.Top + newSize.Height;
break;
}
}
-
+
+ ///
+ /// For an original size, and a selected size, returns the the largest possible size that
+ /// * has the same aspect ratio as the original
+ /// * fits into selected size
+ ///
+ /// size to be considered for keeping aspect ratio
+ /// selection size (i.e. the size we'd produce if we wouldn't keep aspect ratio)
+ ///
+ private static SizeF getNewSizeForRationalScale(SizeF originalSize, SizeF selectedSize)
+ {
+ SizeF newSize = selectedSize;
+ float originalRatio = originalSize.Width / originalSize.Height;
+ float selectedRatio = selectedSize.Width / selectedSize.Height;
+ // will fix orientation if the scaling causes size to be flipped in any direction
+ int flippedRatioSign = Math.Sign(selectedRatio) * Math.Sign(originalRatio);
+ if (Math.Abs(selectedRatio) > Math.Abs(originalRatio))
+ {
+ // scaled rectangle (ratio) would be wider than original
+ // keep height and tweak width to maintain aspect ratio
+ newSize.Width = selectedSize.Height * originalRatio * flippedRatioSign;
+ }
+ else if (Math.Abs(selectedRatio) < Math.Abs(originalRatio))
+ {
+ // scaled rectangle (ratio) would be taller than original
+ // keep width and tweak height to maintain aspect ratio
+ newSize.Height = selectedSize.Width / originalRatio * flippedRatioSign;
+ }
+ return newSize;
+ }
+
public static void Scale(Rectangle boundsBeforeResize, int cursorX, int cursorY, ref RectangleF boundsAfterResize) {
Scale(boundsBeforeResize, cursorX, cursorY, ref boundsAfterResize, null);
}