我的2D引擎与分辨率无关,并且有一个基于以下文章的相机:http://www.david-gouveia.com/portfolio/2d-camera-with-parallax-scrolling-in-xna/
我已经实现了视差滚动到我的相机类中,就像上面提到的那样。它工作得很好,但它搞砸了我的剔除代码,我很难弄清楚数学。
我的每张背景图片都有一个矩形,用于检查它当前是否在屏幕上。如果它没有与我的相机矩形相撞,我就不能画它。问题在于,如果图像是作为视差图层绘制的,则不会计算矩形在屏幕上真正显示的位置。
我的Camera类中的变换矩阵如下所示:
public static Matrix GetTransformMatrix(Vector2 parallax)
{
return Matrix.CreateTranslation(new Vector3(-position * parallax, 0)) * Matrix.CreateRotationZ(rotation) *
Matrix.CreateScale(new Vector3(zoom, zoom, 1)) * Matrix.CreateTranslation(new Vector3(Resolution.VirtualWidth
* 0.5f, Resolution.VirtualHeight * 0.5f, 0));
}
对于每个视差层,我调用SpriteBatch.Begin()并传递上面的变换矩阵,并传递正确的视差偏移,具体取决于我们绘制的图层(前景,背景等)
我已成功制作了一个ScreenToWorld功能,可以获取点击鼠标的位置。请注意,我需要计算我的分辨率矩阵和相机矩阵才能工作。
public static Vector2 ScreenToWorld(Vector2 input, Vector2 parallax)
{
input.X -= Resolution.VirtualViewportX;
input.Y -= Resolution.VirtualViewportY;
Vector2 resPosition = Vector2.Transform(input, Matrix.Invert(Resolution.getTransformationMatrix()));
Vector2 finalPosition = Vector2.Transform(resPosition, Matrix.Invert(Camera.GetTransformMatrix(parallax)));
return finalPosition;
}
所以我想计算我的视差图层的正确矩形位置我需要一个WorldToScreen函数......我试过这个,但它没有工作:
public static Vector2 WorldToScreen(Vector2 input, Vector2 parallax) //I pass the same parallax value that is used in the Camera matrix function.
{
input.X -= Resolution.VirtualViewportX;
input.Y -= Resolution.VirtualViewportY;
Vector2 resPosition = Vector2.Transform(input, Resolution.getTransformationMatrix());
Vector2 finalPosition = Vector2.Transform(resPosition, Camera.GetTransformMatrix(parallax));
return finalPosition;
}
我猜我在正确的轨道上,但我的数学错了?我将上述函数传递给非视差矩形位置,希望将其更新到实际绘制视差图像的位置。如果有人可以提供帮助,请提前致谢!
答案 0 :(得分:0)
结束我的数学运算是正确的,但我需要根据相机的矩阵计算我的相机的屏幕矩形。如果你这样做,你根本不需要触摸背景矩形。只需将背景的视差值传入此函数,然后检查它返回的矩形:
/// <summary>
/// Calculates the Camera's screenRect based on the parallax value passed in.
/// </summary>
public static Rectangle VisibleArea(Vector2 parallax)
{
Matrix inverseViewMatrix = Matrix.Invert(GetTransformMatrix(parallax));
Vector2 tl = Vector2.Transform(Vector2.Zero, inverseViewMatrix);
Vector2 tr = Vector2.Transform(new Vector2(Resolution.VirtualWidth, 0), inverseViewMatrix);
Vector2 bl = Vector2.Transform(new Vector2(0, Resolution.VirtualHeight), inverseViewMatrix);
Vector2 br = Vector2.Transform(new Vector2(Resolution.VirtualWidth, Resolution.VirtualHeight), inverseViewMatrix);
Vector2 min = new Vector2(
MathHelper.Min(tl.X, MathHelper.Min(tr.X, MathHelper.Min(bl.X, br.X))),
MathHelper.Min(tl.Y, MathHelper.Min(tr.Y, MathHelper.Min(bl.Y, br.Y))));
Vector2 max = new Vector2(
MathHelper.Max(tl.X, MathHelper.Max(tr.X, MathHelper.Max(bl.X, br.X))),
MathHelper.Max(tl.Y, MathHelper.Max(tr.Y, MathHelper.Max(bl.Y, br.Y))));
return new Rectangle((int)min.X, (int)min.Y, (int)(max.X - min.X), (int)(max.Y - min.Y));
}