, .
, , 2 , , . , .

double CalculateConstraintScale(double rotation, int pixelWidth, int pixelHeight)
( # ):
- , .
** Note. Although many mathematical operations can be performed using matrix operations, calculations are not enough for this. I also thought that this would be the best example of the first principles. *
C # code:
private double CalculateConstraintScale(double rotation, int pixelWidth, int pixelHeight)
{
double rotationRadians = rotation * PiDiv180;
double width = pixelWidth / 2.0;
double height = pixelHeight / 2.0;
double radius = Math.Sqrt(width * width + height * height);
double angle = Math.Atan(height / width);
double angle2 = Math.Atan(height / -width);
angle += rotationRadians;
angle2 += rotationRadians;
double x = Math.Abs(radius * Math.Cos(angle));
double y = Math.Abs(radius * Math.Sin(angle));
double x2 = Math.Abs(radius * Math.Cos(angle2));
double y2 = Math.Abs(radius * Math.Sin(angle2));
x = Math.Max(x, x2);
y = Math.Max(y, y2);
double deltaX = x - width;
double deltaY = y - height;
return (deltaX > deltaY) ? width / x : height / y;
}
Usage example:
private WriteableBitmap GenerateConstrainedBitmap(BitmapImage sourceImage, int pixelWidth, int pixelHeight, double rotation)
{
double scale = CalculateConstraintScale(rotation, pixelWidth, pixelHeight);
var transform = new TransformGroup();
var rt = new RotateTransform()
{
Angle = rotation,
CenterX = (pixelWidth / 2.0),
CenterY = (pixelHeight / 2.0)
};
transform.Children.Add(rt);
var st = new ScaleTransform()
{
ScaleX = scale,
ScaleY = scale,
CenterX = (pixelWidth / 2.0),
CenterY = (pixelHeight / 2.0)
};
transform.Children.Add(st);
var tempImage = new Image()
{
Stretch = Stretch.Fill,
Width = pixelWidth,
Height = pixelHeight,
Source = sourceImage,
};
tempImage.UpdateLayout();
var writeableBitmap = new WriteableBitmap(pixelWidth, pixelHeight);
writeableBitmap.Render(tempImage, transform);
writeableBitmap.Invalidate();
return writeableBitmap;
}
I released a test layer of code on my website so you can actually try it - click to try
PS Yes, this is my answer from another question, which is repeated exactly, but the question requires the same answer as the one that will be complete.