为离屏渲染移动 UWP InkStrokes
Moving UWP InkStrokes for Offscreen Rendering
我正在捕获 InkStrokes 并且需要在背景中创建笔划的缩放位图图像。无论墨水的边界框有多大,捕获的图像都需要具有统一的大小。
例如,如果绘制原始墨迹笔划并且边界框 top/left 为 100,100 且墨迹上的大小为 200,200 canvas,我希望墨迹从 0,0 开始大小为 50,50 的新渲染位图(现在忽略笔划宽度的影响)。
我已经想出如何缩放墨迹笔划(感谢 )但不知道如何移动笔划。现在,我似乎必须创建一个 InkCanvas 大小的位图,渲染缩放的墨水,然后将更大的图像裁剪为正确的大小。
我已经尝试使用 InkStroke.PointTranslate 通过
var scaleMatrix = Matrix3x2.CreateScale(scale);
scaleMatrix.Translation = -offset; // top/left of ink stroke bounding box
stroke.PointTransform = scaleMatrix;
但是坐标不正确
非常感谢任何帮助。
您可以通过乘以矩阵来组合变换。这对我有用
var strokes = inkCanvas.InkPresenter.StrokeContainer.GetStrokes();
var boundingBox = inkCanvas.InkPresenter.StrokeContainer.BoundingRect;
var matrix1 = Matrix3x2.CreateTranslation((float)-boundingBox.X, (float)-boundingBox.Y);
var matrix2 = Matrix3x2.CreateScale(0.5f);
var builder = new InkStrokeBuilder();
var newStrokeList = new List<InkStroke>();
foreach (var stroke in strokes)
{
newStrokeList.Add(builder.CreateStrokeFromInkPoints
(stroke.GetInkPoints(), matrix1 * matrix2));
}
//Add the translated and scaled strokes to the inkcanvas
inkCanvas.InkPresenter.StrokeContainer.AddStrokes(newStrokeList);
也许我还是做错了什么,但看来您不能将 InkStrokeBuilder.CreateStrokeFromInkPoints 用于不止一种变换。我尝试了各种 combinations/approaches,就是无法正常工作。
这是我的解决方案...
private static IList<InkStroke> GetScaledAndTransformedStrokes(IList<InkStroke> strokeList, float scale)
{
var builder = new InkStrokeBuilder();
var newStrokeList = new List<InkStroke>();
var boundingBox = strokeList.GetBoundingBox();
foreach (var singleStroke in strokeList)
{
var translateMatrix = new Matrix(1, 0, 0, 1, -boundingBox.X, -boundingBox.Y);
var newInkPoints = new List<InkPoint>();
var originalInkPoints = singleStroke.GetInkPoints();
foreach (var point in originalInkPoints)
{
var newPosition = translateMatrix.Transform(point.Position);
var newInkPoint = new InkPoint(newPosition, point.Pressure, point.TiltX, point.TiltY, point.Timestamp);
newInkPoints.Add(newInkPoint);
}
var newStroke = builder.CreateStrokeFromInkPoints(newInkPoints, new Matrix3x2(scale, 0, 0, scale, 0, 0));
newStrokeList.Add(newStroke);
}
return newStrokeList;
}
我最终不得不应用我自己的翻译转换,然后使用 builder.CreateStrokeFromInkPoints 和应用比例矩阵来获得我想要的结果。 GetBoundingBox是我自己的扩展:
public static class RectExtensions
{
public static Rect CombineWith(this Rect r, Rect rect)
{
var top = (r.Top < rect.Top) ? r.Top : rect.Top;
var left = (r.Left < rect.Left) ? r.Left : rect.Left;
var bottom = (r.Bottom < rect.Bottom) ? rect.Bottom : r.Bottom;
var right = (r.Right < rect.Right) ? rect.Right : r.Right;
var newRect = new Rect(new Point(left, top), new Point(right, bottom));
return newRect;
}
}
我正在捕获 InkStrokes 并且需要在背景中创建笔划的缩放位图图像。无论墨水的边界框有多大,捕获的图像都需要具有统一的大小。
例如,如果绘制原始墨迹笔划并且边界框 top/left 为 100,100 且墨迹上的大小为 200,200 canvas,我希望墨迹从 0,0 开始大小为 50,50 的新渲染位图(现在忽略笔划宽度的影响)。
我已经想出如何缩放墨迹笔划(感谢
我已经尝试使用 InkStroke.PointTranslate 通过
var scaleMatrix = Matrix3x2.CreateScale(scale);
scaleMatrix.Translation = -offset; // top/left of ink stroke bounding box
stroke.PointTransform = scaleMatrix;
但是坐标不正确
非常感谢任何帮助。
您可以通过乘以矩阵来组合变换。这对我有用
var strokes = inkCanvas.InkPresenter.StrokeContainer.GetStrokes();
var boundingBox = inkCanvas.InkPresenter.StrokeContainer.BoundingRect;
var matrix1 = Matrix3x2.CreateTranslation((float)-boundingBox.X, (float)-boundingBox.Y);
var matrix2 = Matrix3x2.CreateScale(0.5f);
var builder = new InkStrokeBuilder();
var newStrokeList = new List<InkStroke>();
foreach (var stroke in strokes)
{
newStrokeList.Add(builder.CreateStrokeFromInkPoints
(stroke.GetInkPoints(), matrix1 * matrix2));
}
//Add the translated and scaled strokes to the inkcanvas
inkCanvas.InkPresenter.StrokeContainer.AddStrokes(newStrokeList);
也许我还是做错了什么,但看来您不能将 InkStrokeBuilder.CreateStrokeFromInkPoints 用于不止一种变换。我尝试了各种 combinations/approaches,就是无法正常工作。
这是我的解决方案...
private static IList<InkStroke> GetScaledAndTransformedStrokes(IList<InkStroke> strokeList, float scale)
{
var builder = new InkStrokeBuilder();
var newStrokeList = new List<InkStroke>();
var boundingBox = strokeList.GetBoundingBox();
foreach (var singleStroke in strokeList)
{
var translateMatrix = new Matrix(1, 0, 0, 1, -boundingBox.X, -boundingBox.Y);
var newInkPoints = new List<InkPoint>();
var originalInkPoints = singleStroke.GetInkPoints();
foreach (var point in originalInkPoints)
{
var newPosition = translateMatrix.Transform(point.Position);
var newInkPoint = new InkPoint(newPosition, point.Pressure, point.TiltX, point.TiltY, point.Timestamp);
newInkPoints.Add(newInkPoint);
}
var newStroke = builder.CreateStrokeFromInkPoints(newInkPoints, new Matrix3x2(scale, 0, 0, scale, 0, 0));
newStrokeList.Add(newStroke);
}
return newStrokeList;
}
我最终不得不应用我自己的翻译转换,然后使用 builder.CreateStrokeFromInkPoints 和应用比例矩阵来获得我想要的结果。 GetBoundingBox是我自己的扩展:
public static class RectExtensions
{
public static Rect CombineWith(this Rect r, Rect rect)
{
var top = (r.Top < rect.Top) ? r.Top : rect.Top;
var left = (r.Left < rect.Left) ? r.Left : rect.Left;
var bottom = (r.Bottom < rect.Bottom) ? rect.Bottom : r.Bottom;
var right = (r.Right < rect.Right) ? rect.Right : r.Right;
var newRect = new Rect(new Point(left, top), new Point(right, bottom));
return newRect;
}
}