/// <summary> /// Called when a mesh should be generated for the shape. /// </summary> /// <param name="absoluteDistanceThreshold">The absolute distance threshold.</param> /// <param name="iterationLimit">The iteration limit.</param> /// <returns>The triangle mesh for this shape.</returns> protected override TriangleMesh OnGetMesh(float absoluteDistanceThreshold, int iterationLimit) { // Convert absolute error to relative error. float maxExtent = GetAabb(Vector3F.One, Pose.Identity).Extent.LargestComponent; float relativeThreshold = !Numeric.IsZero(maxExtent) ? absoluteDistanceThreshold / maxExtent : Numeric.EpsilonF; // Get meshes of children and add them to mesh in parent space. TriangleMesh mesh = new TriangleMesh(); int numberOfGeometries = Children.Count; for (int childIndex = 0; childIndex < numberOfGeometries; childIndex++) { IGeometricObject geometricObject = Children[childIndex]; // Get child mesh. var childMesh = geometricObject.Shape.GetMesh(relativeThreshold, iterationLimit); // Transform child mesh into local space of this parent shape. childMesh.Transform(geometricObject.Pose.ToMatrix44F() * Matrix44F.CreateScale(geometricObject.Scale)); // Add to parent mesh. mesh.Add(childMesh, false); } return(mesh); }
public WpRagdollSample(Microsoft.Xna.Framework.Game game) : base(game) { GraphicsScreen.ClearBackground = true; GraphicsScreen.BackgroundColor = Color.CornflowerBlue; // Set a fixed camera. var projection = new PerspectiveProjection(); projection.SetFieldOfView( MathHelper.ToRadians(30), GraphicsService.GraphicsDevice.Viewport.AspectRatio, 1f, 100.0f); Vector3F cameraTarget = new Vector3F(0, 1, 0); Vector3F cameraPosition = new Vector3F(0, 12, 0); Vector3F cameraUpVector = new Vector3F(0, 0, -1); GraphicsScreen.CameraNode = new CameraNode(new Camera(projection)) { View = Matrix44F.CreateLookAt(cameraPosition, cameraTarget, cameraUpVector), }; InitializePhysics(); }
private void RenderHiDef(TextureCube texture, Matrix33F orientation, float exposure, RenderContext context) { var graphicsDevice = context.GraphicsService.GraphicsDevice; var savedRenderState = new RenderStateSnapshot(graphicsDevice); graphicsDevice.RasterizerState = RasterizerState.CullNone; graphicsDevice.DepthStencilState = DepthStencilState.DepthRead; graphicsDevice.BlendState = BlendState.Opaque; var cameraNode = context.CameraNode; Matrix44F view = cameraNode.View; Matrix44F projection = cameraNode.Camera.Projection; // Cube maps are left handed --> Sample with inverted z. (Otherwise, the // cube map and objects or texts in it are mirrored.) var mirrorZ = Matrix44F.CreateScale(1, 1, -1); _parameterWorldViewProjection.SetValue( (Matrix)(projection * view * new Matrix44F(orientation, Vector3F.Zero) * mirrorZ)); _parameterExposure.SetValue(new Vector4(exposure, exposure, exposure, 1)); _textureParameter.SetValue(texture); if (context.IsHdrEnabled()) { _passLinear.Apply(); } else { _passGamma.Apply(); } _submesh.Draw(); savedRenderState.Restore(); }
public void NoRenderTexture() { var tc = new TestCore(); tc.Init(); var texture = Texture2D.Load(@"../../Core/TestData/IO/AltseedPink.png"); Assert.NotNull(texture); var node = new SpriteNode(); node.Src = new RectF(new Vector2F(100, 100), new Vector2F(200, 200)); node.Texture = texture; node.Pivot = texture.Size / 2; node.CameraGroup = 1 << 0; Engine.AddNode(node); var camera = new CameraNode(); camera.Transform = Matrix44F.GetTranslation2D(new Vector2F(-200, -200)); camera.Group = 0; Engine.AddNode(camera); tc.LoopBody(c => { node.Angle++; } , null); tc.End(); }
public void RenderedCamera() { var tc = new TestCore(); tc.Init(); var texture = Altseed2.RenderTexture.Create(new Vector2I(100, 100), TextureFormat.R8G8B8A8_UNORM); Assert.NotNull(texture); var camera1 = Altseed2.RenderedCamera.Create(); Assert.NotNull(camera1); camera1.ViewMatrix = Matrix44F.GetTranslation2D(new Vector2F(10, 10)); camera1.TargetTexture = texture; const string path = "Serialization/RenderedCamera.bin"; Serialize(path, camera1); var camera2 = Deserialize <RenderedCamera>(path); Assert.NotNull(camera2); Assert.AreEqual(camera1.RenderPassParameter.ClearColor, camera2.RenderPassParameter.ClearColor); Assert.AreEqual(camera1.RenderPassParameter.IsColorCleared, camera2.RenderPassParameter.IsColorCleared); Assert.AreEqual(camera1.RenderPassParameter.IsDepthCleared, camera2.RenderPassParameter.IsDepthCleared); Assert.AreEqual(camera1.TargetTexture.Size, camera2.TargetTexture.Size); Assert.AreEqual(camera1.ViewMatrix, camera2.ViewMatrix); tc.End(); }
public void CompositeShapeWithRotatedChildren() { var s = new CompositeShape(); s.Children.Add(new GeometricObject(new BoxShape(1, 2, 3), new Vector3F(1.1f, 0.3f, 0.8f), new Pose(new Vector3F(100, 10, 0), RandomHelper.Random.NextQuaternionF()))); s.Children.Add(new GeometricObject(new ConeShape(1, 2), new Vector3F(1.1f, 0.3f, 0.8f), new Pose(new Vector3F(-10, -10, 0), RandomHelper.Random.NextQuaternionF()))); float m0; Vector3F com0; Matrix33F i0; MassHelper.GetMass(s, new Vector3F(2), 1, true, 0.001f, 10, out m0, out com0, out i0); var m = s.GetMesh(0.001f, 6); m.Transform(Matrix44F.CreateScale(2)); float m1; Vector3F com1; Matrix33F i1; MassHelper.GetMass(m, out m1, out com1, out i1); const float e = 0.01f; Assert.IsTrue(Numeric.AreEqual(m0, m1, e * (1 + m0))); Assert.IsTrue(Vector3F.AreNumericallyEqual(com0, com1, e * (1 + com0.Length))); Assert.IsTrue(Matrix33F.AreNumericallyEqual(i0, i1, e * (1 + i0.Trace))); }
public void SetProjectionOffCenterTest() { OrthographicProjection projection = new OrthographicProjection(); projection.SetOffCenter(0, 4, 1, 4, 2, 10); OrthographicProjection camera2 = new OrthographicProjection(); camera2.SetOffCenter(0, 4, 1, 4); camera2.Near = 2; camera2.Far = 10; Projection camera3 = new OrthographicProjection { Left = 0, Right = 4, Bottom = 1, Top = 4, Near = 2, Far = 10, }; Matrix44F expected = Matrix44F.CreateOrthographicOffCenter(0, 4, 1, 4, 2, 10); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, projection)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, camera2)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, camera3.ToMatrix44F())); }
public void SetProjectionTest() { OrthographicProjection projection = new OrthographicProjection(); projection.Set(4, 3, 2, 10); OrthographicProjection camera2 = new OrthographicProjection(); camera2.Set(4, 3); camera2.Near = 2; camera2.Far = 10; OrthographicProjection camera3 = new OrthographicProjection { Left = -2, Right = 2, Bottom = -1.5f, Top = 1.5f, Near = 2, Far = 10, }; Matrix44F expected = Matrix44F.CreateOrthographic(4, 3, 2, 10); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, projection)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, camera2)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, camera3.ToMatrix44F())); }
public void ScaledConvexMass() { var s = new ScaledConvexShape(new CapsuleShape(1, 3), new Vector3F(0.9f, -0.8f, 1.2f)); float m0; Vector3F com0; Matrix33F i0; MassHelper.GetMass(s, new Vector3F(1, -2, -3), 1, true, 0.001f, 10, out m0, out com0, out i0); var m = s.GetMesh(0.001f, 6); m.Transform(Matrix44F.CreateScale(1, -2, -3)); float m1; Vector3F com1; Matrix33F i1; MassHelper.GetMass(m, out m1, out com1, out i1); const float e = 0.01f; Assert.IsTrue(Numeric.AreEqual(m0, m1, e * (1 + m0))); Assert.IsTrue(Vector3F.AreNumericallyEqual(com0, com1, e * (1 + com0.Length))); Assert.IsTrue(Matrix33F.AreNumericallyEqual(i0, i1, e * (1 + i0.Trace))); // Try other density. float m2; Vector3F com2; Matrix33F i2; MassHelper.GetMass(s, new Vector3F(1, -2, -3), 0.7f, true, 0.001f, 10, out m2, out com2, out i2); Assert.IsTrue(Numeric.AreEqual(m0 * 0.7f, m2, e * (1 + m0))); Assert.IsTrue(Vector3F.AreNumericallyEqual(com0, com2, e * (1 + com0.Length))); Assert.IsTrue(Matrix33F.AreNumericallyEqual(i0 * 0.7f, i2, e * (1 + i0.Trace))); }
/// <summary> /// Creates an perspective projection from a 4x4 transformation matrix. /// </summary> /// <param name="matrix">The projection matrix.</param> /// <returns>The perspective projection.</returns> public static PerspectiveProjection FromMatrix(Matrix44F matrix) { var projection = new PerspectiveProjection(); projection.Set(matrix); return(projection); }
public void IsValid() { Matrix44F inValidPose = new Matrix44F(new float[, ] { { 1, 2, 3, 0 }, { 4, 5, 6, 0 }, { 7, 8, 9, 0 }, { 0, 0, 0, 1 }, }); Assert.IsFalse(Pose.IsValid(inValidPose)); Assert.IsTrue(Pose.IsValid(Matrix44F.CreateRotationZ(0.3f))); inValidPose = new Matrix44F(new float[, ] { { 1, 0, 0, 0 }, { 0, 1, 0, 0 }, { 0, 0, 1, 0 }, { 0, 1, 0, 1 }, }); Assert.IsFalse(Pose.IsValid(inValidPose)); inValidPose = new Matrix44F(new float[, ] { { 1, 0, 0, 0 }, { 0, 1, 0, 0 }, { 0, 0, -1, 0 }, { 0, 1, 0, 1 }, }); Assert.IsFalse(Pose.IsValid(inValidPose)); }
public void PoseTest() { CameraInstance cameraInstance = new CameraInstance(new Camera(new PerspectiveProjection())); Assert.IsNotNull(cameraInstance.PoseWorld); Assert.AreEqual(Vector3F.Zero, cameraInstance.PoseWorld.Position); Assert.AreEqual(Matrix33F.Identity, cameraInstance.PoseWorld.Orientation); // Set new Pose Vector3F position = new Vector3F(1, 2, 3); QuaternionF orientation = QuaternionF.CreateRotation(new Vector3F(3, 4, 5), 0.123f); cameraInstance.PoseWorld = new Pose(position, orientation); Assert.AreEqual(position, cameraInstance.PoseWorld.Position); Assert.AreEqual(orientation.ToRotationMatrix33(), cameraInstance.PoseWorld.Orientation); Assert.IsTrue(Matrix44F.AreNumericallyEqual(cameraInstance.PoseWorld.ToMatrix44F(), cameraInstance.ViewInverse)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(cameraInstance.PoseWorld.Inverse.ToMatrix44F(), cameraInstance.View)); // Set Position and Orientation position = new Vector3F(5, 6, 7); orientation = QuaternionF.CreateRotation(new Vector3F(1, -1, 6), -0.123f); cameraInstance.PoseWorld = new Pose(position, orientation); Assert.AreEqual(position, cameraInstance.PoseWorld.Position); Assert.AreEqual(orientation.ToRotationMatrix33(), cameraInstance.PoseWorld.Orientation); Assert.IsTrue(Matrix44F.AreNumericallyEqual(cameraInstance.PoseWorld.Inverse.ToMatrix44F(), cameraInstance.View)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(cameraInstance.PoseWorld.ToMatrix44F(), cameraInstance.ViewInverse)); }
private void SetCameraPose() { var vehiclePose = _vehicle.Pose; if (_useSpectatorView) { // Spectator Mode: // Camera is looking at the car from a fixed location in the level. Vector3F position = new Vector3F(10, 8, 10); Vector3F target = vehiclePose.Position; Vector3F up = Vector3F.UnitY; // Set the new camera view matrix. (Setting the View matrix changes the Pose. // The pose is simply the inverse of the view matrix). CameraNode.View = Matrix44F.CreateLookAt(position, target, up); } else { // Player Camera: // Camera moves with the car. The look direction can be changed by moving the mouse. Matrix33F yaw = Matrix33F.CreateRotationY(_yaw); Matrix33F pitch = Matrix33F.CreateRotationX(_pitch); Matrix33F orientation = vehiclePose.Orientation * yaw * pitch; Vector3F forward = orientation * -Vector3F.UnitZ; Vector3F up = Vector3F.UnitY; Vector3F position = vehiclePose.Position - 10 * forward + 5 * up; Vector3F target = vehiclePose.Position + 1 * up; CameraNode.View = Matrix44F.CreateLookAt(position, target, up); } }
public override void Update(GameTime gameTime) { // Move the directional light in a circle. float deltaTimeF = (float)gameTime.ElapsedGameTime.TotalSeconds; _lightAngle += 0.3f * deltaTimeF; var position = QuaternionF.CreateRotationY(_lightAngle).Rotate(new Vector3F(6, 6, 0)); // Make the light look at the world space origin. var lightTarget = Vector3F.Zero; var lookAtMatrix = Matrix44F.CreateLookAt(position, lightTarget, Vector3F.Up); // A look-at matrix is the inverse of a normal world or pose matrix. _mainDirectionalLightNode.PoseWorld = new Pose(lookAtMatrix.Translation, lookAtMatrix.Minor).Inverse; // Compute shadow matrix for the new light direction. var lightRayDirection = (lightTarget - position); _shadowMatrix = ProjectedShadowRenderer.CreateShadowMatrix( new Plane(new Vector3F(0, 1, 0), 0.01f), new Vector4F(-lightRayDirection, 0)); // Update the scene - this must be called once per frame. _scene.Update(gameTime.ElapsedGameTime); base.Update(gameTime); }
public void GetBoundsOrthographic() { // Get bounds of AABB in clip space. (Used in OcclusionCulling.fx.) Vector3F cameraPosition = new Vector3F(100, -200, 345); Vector3F cameraForward = new Vector3F(1, 2, 3).Normalized; Vector3F cameraUp = new Vector3F(-1, 0.5f, -2).Normalized; Matrix44F view = Matrix44F.CreateLookAt(cameraPosition, cameraPosition + cameraForward, cameraUp); Matrix44F proj = Matrix44F.CreateOrthographic(16, 9, -10, 100); Matrix44F viewProj = proj * view; Vector3F center = new Vector3F(); Vector3F halfExtent = new Vector3F(); Aabb aabb = new Aabb(center - halfExtent, center + halfExtent); Aabb aabb0, aabb1; GetBoundsOrtho(aabb, viewProj, out aabb0); GetBoundsOrthoSmart(aabb, viewProj, out aabb1); Assert.IsTrue(Aabb.AreNumericallyEqual(aabb0, aabb1)); center = new Vector3F(-9, 20, -110); halfExtent = new Vector3F(5, 2, 10); aabb = new Aabb(center - halfExtent, center + halfExtent); GetBoundsOrtho(aabb, viewProj, out aabb0); GetBoundsOrthoSmart(aabb, viewProj, out aabb1); Assert.IsTrue(Aabb.AreNumericallyEqual(aabb0, aabb1)); }
public void GetMesh(Shape shape, out Submesh submesh, out Matrix44F matrix) { ThrowIfDisposed(); if (shape == null) throw new ArgumentNullException("shape"); var index = GetCacheIndex(shape); if (index >= 0) { // Found cache entry! var entry = _cache[index]; Debug.Assert(entry.ShapeWeak.Target == shape, "ShapeMeshCache.GetCacheIndex() returned wrong index."); // Get submesh from strong or weak reference. submesh = entry.Submesh ?? (Submesh)entry.SubmeshWeak.Target; matrix = entry.Matrix; if (submesh != null) { // Recreate submesh if number of triangles in TriangleMeshShape has changed. var triangleMeshShape = shape as TriangleMeshShape; if (triangleMeshShape != null && triangleMeshShape.Mesh.NumberOfTriangles != submesh.PrimitiveCount) { DisposeMesh(entry); submesh = null; } } // Recreate submesh if necessary. if (submesh == null) CreateMesh(shape, out submesh, out matrix); _cache[index].Submesh = submesh; _cache[index].Matrix = matrix; _cache[index].Age = 0; } else { // No cache entry found. // GetCacheIndex returns the bitwise complement of the next index. index = ~index; // No submesh in cache. CreateMesh(shape, out submesh, out matrix); var entry = new CacheEntry(shape) { HashCode = _tempEntry.HashCode, Age = 0, Submesh = submesh, Matrix = matrix, }; _cache.Insert(index, entry); // If shape changes, we must invalidate the cache entry: shape.Changed += OnCachedShapeChanged; } }
public void SetProjectionFieldOfViewTest() { PerspectiveProjection projection = new PerspectiveProjection(); projection.SetFieldOfView(MathHelper.ToRadians(60), 16.0f / 9.0f, 1, 10); PerspectiveProjection projection2 = new PerspectiveProjection(); projection2.SetFieldOfView(MathHelper.ToRadians(60), 16.0f / 9.0f); projection2.Near = 1; projection2.Far = 10; Projection projection3 = new PerspectiveProjection { Left = -2.0528009f / 2.0f, Right = 2.0528009f / 2.0f, Bottom = -1.1547005f / 2.0f, Top = 1.1547005f / 2.0f, Near = 1, Far = 10, }; Matrix44F expected = Matrix44F.CreatePerspectiveFieldOfView(MathHelper.ToRadians(60), 16.0f / 9.0f, 1, 10); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, projection)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, projection2)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, projection3.ToMatrix44F())); }
public void SetProjectionTest() { PerspectiveProjection projection = new PerspectiveProjection(); projection.Set(4, 3, 2, 10); PerspectiveProjection projection2 = new PerspectiveProjection(); projection2.Set(4, 3); projection2.Near = 2; projection2.Far = 10; Projection projection3 = new PerspectiveProjection { Left = -2, Right = 2, Bottom = -1.5f, Top = 1.5f, Near = 2, Far = 10, }; Matrix44F expected = Matrix44F.CreatePerspective(4, 3, 2, 10); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, projection)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, projection2)); Assert.IsTrue(Matrix44F.AreNumericallyEqual(expected, projection3.ToMatrix44F())); }
/// <inheritdoc/> protected override Matrix44F ComputeProjection() { var projection = Matrix44F.CreatePerspectiveOffCenter(Left, Right, Bottom, Top, Near, Far); if (_nearClipPlane.HasValue) { Vector4F clipPlane = new Vector4F(_nearClipPlane.Value.Normal, -_nearClipPlane.Value.DistanceFromOrigin); // Calculate the clip-space corner point opposite the clipping plane as // (-sign(clipPlane.x), -sign(clipPlane.y), 1, 1) and transform it into // camera space by multiplying it by the inverse of the projection matrix. Vector4F q; q.X = (-Math.Sign(clipPlane.X) + projection.M02) / projection.M00; q.Y = (-Math.Sign(clipPlane.Y) + projection.M12) / projection.M11; q.Z = -1.0f; q.W = (1.0f + projection.M22) / projection.M23; // Calculate the scaled plane vector Vector4F c = clipPlane * (1.0f / Vector4F.Dot(clipPlane, q)); // Replace the third row of the projection matrix projection.M20 = c.X; projection.M21 = c.Y; projection.M22 = c.Z; projection.M23 = c.W; } return(projection); }
/// <summary> /// Updates the projection matrix. /// </summary> private void Update() { // Let the derived class update the projection. _projection = ComputeProjection(); _projectionInverse = _projection.Inverse; _projectionNeedsToBeUpdated = false; }
/// <summary> /// Creates an orthographic projection from a 4x4 transformation matrix. /// </summary> /// <param name="matrix">The projection matrix.</param> /// <returns>The orthographic projection.</returns> public static OrthographicProjection FromMatrix(Matrix44F matrix) { var projection = new OrthographicProjection(); projection.Set(matrix); return(projection); }
public MyGraphicsScreen(IGraphicsService graphicsService) : base(graphicsService) { _meshRenderer = new MeshRenderer(); var contentManager = ServiceLocator.Current.GetInstance <ContentManager>(); var spriteFont = contentManager.Load <SpriteFont>("SpriteFont1"); _debugRenderer = new DebugRenderer(graphicsService, spriteFont); Scene = new Scene(); // Add a camera with a perspective projection. var projection = new PerspectiveProjection(); projection.SetFieldOfView( ConstantsF.PiOver4, graphicsService.GraphicsDevice.Viewport.AspectRatio, 0.1f, 100.0f); CameraNode = new CameraNode(new Camera(projection)) { Name = "CameraPerspective", PoseWorld = Pose.FromMatrix(Matrix44F.CreateLookAt(new Vector3F(10, 5, 10), new Vector3F(0, 1, 0), new Vector3F(0, 1, 0)).Inverse), }; Scene.Children.Add(CameraNode); }
/// <summary> /// Converts the specified distance to a view-normalized distance ("LOD distance"). /// </summary> /// <param name="distance">The 3D Euclidean distance between the object and the camera.</param> /// <param name="projection">The projection transformation.</param> /// <returns>The view-normalized distance.</returns> /// <inheritdoc cref="GetViewNormalizedDistance(DigitalRune.Graphics.SceneGraph.SceneNode,DigitalRune.Graphics.SceneGraph.CameraNode)"/> public static float GetViewNormalizedDistance(float distance, Matrix44F projection) { Debug.Assert(distance >= 0, "The distance should be greater than or equal to 0."); float yScale = Math.Abs(projection.M11); return(distance / yScale); }
public void RotationMatrix44() { float angle = -1.6f; Vector3F axis = new Vector3F(1.0f, 2.0f, -3.0f); QuaternionF q = QuaternionF.CreateRotation(axis, angle); Matrix44F m44 = Matrix44F.CreateRotation(axis, angle); Assert.IsTrue(Matrix44F.AreNumericallyEqual(q.ToRotationMatrix44(), m44)); }
public static Matrix4x4 ToStandard(this Pose pose) { Matrix44F matrix44F = pose.ToMatrix44F(); return(new Matrix4x4(matrix44F.M00, matrix44F.M10, matrix44F.M20, matrix44F.M30, matrix44F.M01, matrix44F.M11, matrix44F.M21, matrix44F.M31, matrix44F.M02, matrix44F.M12, matrix44F.M22, matrix44F.M31, matrix44F.M03, matrix44F.M13, matrix44F.M23, matrix44F.M33)); }
public void BasicSpriteTexture() { Assert.True(Engine.Initialize("Altseed2 C# Engine", 800, 600, new Configuration())); var count = 0; var t1 = Texture2D.Load(@"../../Core/TestData/IO/AltseedPink.png"); var t2 = Texture2D.Load(@"../../Core/TestData/IO/AltseedPink.jpg"); Assert.NotNull(t1); Assert.NotNull(t2); var s1 = RenderedSprite.Create(); var s1_2 = RenderedSprite.Create(); var s1_3 = RenderedSprite.Create(); var s2 = RenderedSprite.Create(); s1.Texture = t1; s1.Src = new RectF(0, 0, 128, 128); var trans = new Matrix44F(); trans.SetTranslation(100, 200, 0); s1_2.Texture = t1; s1_2.Transform = trans; s1_2.Src = new RectF(128, 128, 256, 256); trans = new Matrix44F(); trans.SetTranslation(200, 200, 0); s1_3.Texture = t1; s1_3.Transform = trans; s1_3.Src = new RectF(128, 128, 256, 256); trans = new Matrix44F(); trans.SetTranslation(200, 200, 0); s2.Texture = t2; s2.Transform = trans; s2.Src = new RectF(128, 128, 256, 256); while (Engine.DoEvents() && count++ < 300) { Assert.True(Engine.Graphics.BeginFrame()); Engine.Renderer.DrawSprite(s1); Engine.Renderer.DrawSprite(s1_2); Engine.Renderer.DrawSprite(s2); Engine.Update(); var cmdList = Engine.Graphics.CommandList; cmdList.SetRenderTargetWithScreen(); Engine.Renderer.Render(cmdList); Assert.True(Engine.Graphics.EndFrame()); } Engine.Terminate(); }
/// <summary> /// Converts EasyAR matrix objects to Urho matrix objects, note that this does not change the handedness of the matrix. EasyAR matrices /// are in OpenGL format except they are row-major while Urho matrices are in DirectX format. /// </summary> /// <param name="matrix">The matrix as an EasyAR object</param> /// <returns>The matrix as an Urho object</returns> public static Matrix4 ToUrhoMatrix(this Matrix44F matrix) { Matrix4 m4 = new Matrix4( matrix.data_0, matrix.data_1, matrix.data_2, matrix.data_3, matrix.data_4, matrix.data_5, matrix.data_6, matrix.data_7, matrix.data_8, matrix.data_9, matrix.data_10, matrix.data_11, matrix.data_12, matrix.data_13, matrix.data_14, matrix.data_15); return(m4); }
public void IsValidTest() { var m = Matrix44F.CreateTranslation(1, 2, 3) * Matrix44F.CreateRotationY(0.1f) * Matrix44F.CreateScale(-2, 3, 4); Assert.IsTrue(SrtTransform.IsValid(m)); // Concatenating to SRTs creates a skew. m = Matrix44F.CreateRotationZ(0.1f) * Matrix44F.CreateScale(-2, 3, 4) * m; Assert.IsFalse(SrtTransform.IsValid(m)); }
public void Multiply() { var a = new SrtTransform(new Vector3F(1, 2, 7), new QuaternionF(1, 2, 3, 4).Normalized, new Vector3F(4, -5, 6)); var b = new SrtTransform(new Vector3F(-3, 9, -2), new QuaternionF(3, -2, 1, 9).Normalized, new Vector3F(7, -4, 2)); var result1 = SrtTransform.Multiply(a, b).ToMatrix44F(); var result2 = a * b; Assert.IsTrue(Matrix44F.AreNumericallyEqual(result1, result2)); }
public Matrix44F GetProjectionMatrix() { Matrix44F ret = new Matrix44F(EffekseerNativePINVOKE.ViewPointController_GetProjectionMatrix(swigCPtr), true); if (EffekseerNativePINVOKE.SWIGPendingException.Pending) { throw EffekseerNativePINVOKE.SWIGPendingException.Retrieve(); } return(ret); }
public GjkProblemTest(Microsoft.Xna.Framework.Game game) : base(game) { SampleFramework.IsMouseVisible = false; GraphicsScreen.ClearBackground = true; SetCamera(new Vector3F(0, 1, 10), 0, 0); var points1a = new List<Vector3F> { new Vector3F(0.0f, 0.0f, -0.1875f), new Vector3F(0.0f, 0.0f, 0.1875f), new Vector3F(10.0f, 0.0f, -0.1875f), new Vector3F(10.0f, 0.0f, 0.1875f), new Vector3F(10.0f, 5.0f, -0.1875f), new Vector3F(10.0f, 5.0f, 0.1875f), new Vector3F(0.0f, 5.0f, -0.1875f), new Vector3F(0.0f, 5.0f, 0.1875f) }; var points1b = new List<Vector3F> { new Vector3F(0.0f, 0.0f, -0.1875f), new Vector3F(10.0f, 0.0f, -0.1875f), new Vector3F(10.0f, 5.0f, -0.1875f), new Vector3F(0.0f, 5.0f, -0.1875f), new Vector3F(0.0f, 0.0f, 0.1875f), new Vector3F(10.0f, 0.0f, 0.1875f), new Vector3F(10.0f, 5.0f, 0.1875f), new Vector3F(0.0f, 5.0f, 0.1875f) }; var matrix1 = new Matrix44F(0.0f, 1.0f, 0.0f, 208.5f, -1.0f, 0.0f, 0.0f, 10.0f, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f); _part1A = new CollisionObject(new GeometricObject(new ConvexPolyhedron(points1a), Pose.FromMatrix(matrix1))); _part1B = new CollisionObject(new GeometricObject(new ConvexPolyhedron(points1b), Pose.FromMatrix(matrix1))); var points2 = new List<Vector3F> { new Vector3F(0.0f, 0.0f, -0.375f), new Vector3F(0.0f, 0.0f, 0.375f), new Vector3F(23.0f, 0.0f, -0.375f), new Vector3F(23.0f, 0.0f, 0.375f), new Vector3F(23.0f, 10.0f, -0.375f), new Vector3F(23.0f, 10.0f, 0.375f), new Vector3F(0.0f, 10.0f, -0.375f), new Vector3F(0.0f, 10.0f, 0.375f) }; var matrix2 = new Matrix44F(0.0f, 0.0f, -1.0f, 208.125f, 1.0f, 0.0f, 0.0f, 0.0f, 0.0f, -1.0f, 0.0f, 5.0f, 0.0f, 0.0f, 0.0f, 1.0f); _part2 = new CollisionObject(new GeometricObject(new ConvexPolyhedron(points2), Pose.FromMatrix(matrix2))); }
public void Update(float deltaTime, Matrix44F world) { if (deltaTime <= 0) return; // Reset bone transform. SkeletonPose.SetBoneTransform(BoneIndex, SrtTransform.Identity); // Get new fixed point position in world space. var bonePoseAbsolute = SkeletonPose.GetBonePoseAbsolute(BoneIndex); var bonePoseWorld = world * bonePoseAbsolute; var fixedPointPosition = bonePoseWorld.TransformPosition(Offset); // If we haven't set the fixed point position before, then store the position // and we are done. if (_fixedPointPosition.IsNaN) { _fixedPointPosition = fixedPointPosition; return; } // New position and velocity of fixed point. _fixedPointVelocity = (fixedPointPosition - _fixedPointPosition) / deltaTime; _fixedPointPosition = fixedPointPosition; // If the particle position was not set before, then we only store the current values. // The real work starts in the next frame. if (_particlePosition.IsNaN) { _particlePosition = _fixedPointPosition; _particleVelocity = _fixedPointVelocity; return; } // Compute the spring force between the particle and the fixed point. var force = Spring * (_fixedPointPosition - _particlePosition) + Damping * (_fixedPointVelocity - _particleVelocity); // Update velocity and position of the particle using symplectic Euler. _particleVelocity = _particleVelocity + force * deltaTime; _particlePosition = _particlePosition + _particleVelocity * deltaTime; // Convert particle position back to bone space. var particleLocal = bonePoseWorld.Inverse.TransformPosition(_particlePosition); // Create rotation between the fixed point vector and the particle vector. var boneTransform = new SrtTransform(QuaternionF.CreateRotation(Offset, particleLocal)); SkeletonPose.SetBoneTransform(BoneIndex, boneTransform); }
public void Absolute() { Matrix44F absoluteM = new Matrix44F(-1, -2, -3, -4, -5, -6, -7, -8, -9, -10, -11, -12, -13, -14, -15, -16); absoluteM.Absolute(); Assert.AreEqual(1, absoluteM.M00); Assert.AreEqual(2, absoluteM.M01); Assert.AreEqual(3, absoluteM.M02); Assert.AreEqual(4, absoluteM.M03); Assert.AreEqual(5, absoluteM.M10); Assert.AreEqual(6, absoluteM.M11); Assert.AreEqual(7, absoluteM.M12); Assert.AreEqual(8, absoluteM.M13); Assert.AreEqual(9, absoluteM.M20); Assert.AreEqual(10, absoluteM.M21); Assert.AreEqual(11, absoluteM.M22); Assert.AreEqual(12, absoluteM.M23); Assert.AreEqual(13, absoluteM.M30); Assert.AreEqual(14, absoluteM.M31); Assert.AreEqual(15, absoluteM.M32); Assert.AreEqual(16, absoluteM.M33); absoluteM = new Matrix44F(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16); absoluteM.Absolute(); Assert.AreEqual(1, absoluteM.M00); Assert.AreEqual(2, absoluteM.M01); Assert.AreEqual(3, absoluteM.M02); Assert.AreEqual(4, absoluteM.M03); Assert.AreEqual(5, absoluteM.M10); Assert.AreEqual(6, absoluteM.M11); Assert.AreEqual(7, absoluteM.M12); Assert.AreEqual(8, absoluteM.M13); Assert.AreEqual(9, absoluteM.M20); Assert.AreEqual(10, absoluteM.M21); Assert.AreEqual(11, absoluteM.M22); Assert.AreEqual(12, absoluteM.M23); Assert.AreEqual(13, absoluteM.M30); Assert.AreEqual(14, absoluteM.M31); Assert.AreEqual(15, absoluteM.M32); Assert.AreEqual(16, absoluteM.M33); }
public void UpdateClipSubmesh(IGraphicsService graphicsService, LightNode node) { var clip = node.Clip; Debug.Assert(clip != null); // We have to update the submesh if it is null or disposed. // Submesh == null --> Update // Submesh != null && VertexBuffer.IsDisposed --> Update // Submesh != null && VertexBuffer == null --> This is the EmptyShape. No updated needed. if (ClipSubmesh == null || (ClipSubmesh.VertexBuffer != null && ClipSubmesh.VertexBuffer.IsDisposed)) { ShapeMeshCache.GetMesh(graphicsService, clip.Shape, out ClipSubmesh, out ClipMatrix); // Add transform of Clip. ClipMatrix = clip.Pose * Matrix44F.CreateScale(clip.Scale) * ClipMatrix; } }
public ConvexHullSample(Microsoft.Xna.Framework.Game game) : base(game) { SampleFramework.IsMouseVisible = false; GraphicsScreen.ClearBackground = true; GraphicsScreen.BackgroundColor = Color.CornflowerBlue; SetCamera(new Vector3F(0, 1, 10), 0, 0); // Generate random points. var points = new List<Vector3F>(); for (int i = 0; i < 100; i++) points.Add(RandomHelper.Random.NextVector3F(-1, 1)); // Apply random transformation to points to make this sample more interesting. Matrix44F transform = new Matrix44F( Matrix33F.CreateRotation(RandomHelper.Random.NextQuaternionF()) * Matrix33F.CreateScale(RandomHelper.Random.NextVector3F(0.1f, 2f)), RandomHelper.Random.NextVector3F(-1, 1)); for (int i = 0; i < points.Count; i++) points[i] = transform.TransformPosition(points[i]); // Compute convex hull. The result is the mesh of the hull represented as a // Doubly-Connected Edge List (DCEL). DcelMesh convexHull = GeometryHelper.CreateConvexHull(points); // We don't need the DCEL representation. Let's store the hull as a simpler triangle mesh. TriangleMesh convexHullMesh = convexHull.ToTriangleMesh(); // Compute a tight-fitting oriented bounding box. Vector3F boundingBoxExtent; // The bounding box dimensions (widths in X, Y and Z). Pose boundingBoxPose; // The pose (world space position and orientation) of the bounding box. GeometryHelper.ComputeBoundingBox(points, out boundingBoxExtent, out boundingBoxPose); // (Note: The GeometryHelper also contains methods to compute a bounding sphere.) var debugRenderer = GraphicsScreen.DebugRenderer; foreach (var point in points) debugRenderer.DrawPoint(point, Color.White, true); debugRenderer.DrawShape(new TriangleMeshShape(convexHullMesh), Pose.Identity, Vector3F.One, Color.Violet, false, false); debugRenderer.DrawBox(boundingBoxExtent.X, boundingBoxExtent.Y, boundingBoxExtent.Z, boundingBoxPose, Color.Red, true, false); }
public static Vector3F Unproject(this Viewport viewport, Vector3F position, Matrix44F projection, Matrix44F view) { Matrix44F worldViewProjection = projection * view; return Unproject(viewport, position, worldViewProjection); }
public static Vector3F Unproject(this Viewport viewport, Vector3F position, Matrix44F projection) { Matrix44F fromClipSpace = projection.Inverse; Vector3F positionClip = new Vector3F { X = (position.X - viewport.X) / viewport.Width * 2f - 1f, Y = -((position.Y - viewport.Y) / viewport.Height * 2f - 1f), Z = (position.Z - viewport.MinDepth) / (viewport.MaxDepth - viewport.MinDepth), }; // Transform position from clip space to the desired coordinate space. // (TransformPosition() undoes the homogeneous divide and transforms the // position from clip space to the desired coordinate space.) return fromClipSpace.TransformPosition(positionClip); }
public void ExplicitToXnaCast() { Matrix44F v = new Matrix44F(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16); Matrix xna = (Matrix)v; Assert.AreEqual(xna.M11, v.M00); Assert.AreEqual(xna.M12, v.M10); Assert.AreEqual(xna.M13, v.M20); Assert.AreEqual(xna.M14, v.M30); Assert.AreEqual(xna.M21, v.M01); Assert.AreEqual(xna.M22, v.M11); Assert.AreEqual(xna.M23, v.M21); Assert.AreEqual(xna.M24, v.M31); Assert.AreEqual(xna.M31, v.M02); Assert.AreEqual(xna.M32, v.M12); Assert.AreEqual(xna.M33, v.M22); Assert.AreEqual(xna.M34, v.M32); Assert.AreEqual(xna.M41, v.M03); Assert.AreEqual(xna.M42, v.M13); Assert.AreEqual(xna.M43, v.M23); Assert.AreEqual(xna.M44, v.M33); }
/// <summary> /// Projects a position from world space into screen space. /// </summary> /// <param name="viewport">The viewport.</param> /// <param name="position">The position in view space.</param> /// <param name="projection">The projection matrix.</param> /// <returns> /// The position in screen space: The x- and y-components define the pixel position. The /// z-component defines the depth in clip space mapped to the range /// [<see cref="Viewport.MinDepth"/>, <see cref="Viewport.MaxDepth"/>] (usually [0, 1]). /// </returns> public static Vector3F Project(this Viewport viewport, Vector3F position, Matrix44F projection) { // Transform position to clip space. (TransformPosition() transforms the position // to clip space and performs the homogeneous divide.) Vector3F positionClip = projection.TransformPosition(position); Vector3F positionScreen = new Vector3F { X = (1f + positionClip.X) * 0.5f * viewport.Width + viewport.X, Y = (1f - positionClip.Y) * 0.5f * viewport.Height + viewport.Y, Z = positionClip.Z * (viewport.MaxDepth - viewport.MinDepth) + viewport.MinDepth }; return positionScreen; }
public void ClampToZeroStatic() { Matrix44F m = new Matrix44F(0.000001f); Assert.AreEqual(new Matrix44F(), Matrix44F.ClampToZero(m)); Assert.AreEqual(new Matrix44F(0.000001f), m); // m unchanged? m = new Matrix44F(0.1f); Assert.AreEqual(new Matrix44F(0.1f), Matrix44F.ClampToZero(m)); Assert.AreEqual(new Matrix44F(0.1f), m); m = new Matrix44F(0.001f); Assert.AreEqual(new Matrix44F(), Matrix44F.ClampToZero(m, 0.01f)); Assert.AreEqual(new Matrix44F(0.001f), m); m = new Matrix44F(0.1f); Assert.AreEqual(new Matrix44F(0.1f), Matrix44F.ClampToZero(m, 0.01f)); Assert.AreEqual(new Matrix44F(0.1f), m); }
public void Transpose() { Matrix44F m = new Matrix44F(rowMajor, MatrixOrder.RowMajor); m.Transpose(); Matrix44F mt = new Matrix44F(rowMajor, MatrixOrder.ColumnMajor); Assert.AreEqual(mt, m); Matrix44F i = Matrix44F.Identity; i.Transpose(); Assert.AreEqual(Matrix44F.Identity, i); }
/// <summary> /// Sets the orthographic projection from the given projection matrix. /// </summary> /// <param name="projection">The orthographic projection matrix.</param> public override void Set(Matrix44F projection) { string message = "Given matrix is not a valid orthographic projection matrix."; Debug.Assert(Numeric.IsZero(projection.M01), message); Debug.Assert(Numeric.IsZero(projection.M02), message); Debug.Assert(Numeric.IsZero(projection.M10), message); Debug.Assert(Numeric.IsZero(projection.M12), message); Debug.Assert(Numeric.IsZero(projection.M20), message); Debug.Assert(Numeric.IsZero(projection.M21), message); Debug.Assert(Numeric.IsZero(projection.M30), message); Debug.Assert(Numeric.IsZero(projection.M31), message); Debug.Assert(Numeric.IsZero(projection.M32), message); Debug.Assert(Numeric.AreEqual(projection.M33, 1), message); float rightMinusLeft = 2.0f / projection.M00; float leftPlusRight = -projection.M03 * rightMinusLeft; float right = (leftPlusRight + rightMinusLeft) / 2.0f; float left = leftPlusRight - right; Debug.Assert(left < right, message); float topMinusBottom = 2.0f / projection.M11; float bottomPlusTop = -projection.M13 * topMinusBottom; float top = (bottomPlusTop + topMinusBottom) / 2.0f; float bottom = bottomPlusTop - top; Debug.Assert(bottom < top, message); float nearMinusFar = 1.0f / projection.M22; float near = projection.M23 * nearMinusFar; float far = near - nearMinusFar; Debug.Assert(near < far, message); SetOffCenter(left, right, bottom, top, near, far); Invalidate(); }
public void Constructors() { Matrix44F m = new Matrix44F(1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, 8.0f, 9.0f, 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f); for (int i = 0; i < 16; i++) Assert.AreEqual(rowMajor[i], m[i]); m = new Matrix44F(columnMajor, MatrixOrder.ColumnMajor); for (int i = 0; i < 16; i++) Assert.AreEqual(rowMajor[i], m[i]); m = new Matrix44F(rowMajor, MatrixOrder.RowMajor); for (int i = 0; i < 16; i++) Assert.AreEqual(rowMajor[i], m[i]); m = new Matrix44F(new List<float>(columnMajor), MatrixOrder.ColumnMajor); for (int i = 0; i < 16; i++) Assert.AreEqual(rowMajor[i], m[i]); m = new Matrix44F(new List<float>(rowMajor), MatrixOrder.RowMajor); for (int i = 0; i < 16; i++) Assert.AreEqual(rowMajor[i], m[i]); m = new Matrix44F(new float[4, 4] { { 1, 2, 3, 4 }, { 5, 6, 7, 8 }, { 9, 10, 11, 12 }, { 13, 14, 15, 16}}); for (int i = 0; i < 16; i++) Assert.AreEqual(rowMajor[i], m[i]); m = new Matrix44F(new float[4][] { new float[4] { 1, 2, 3, 4 }, new float[4] { 5, 6, 7, 8 }, new float[4] { 9, 10, 11, 12 }, new float[4] { 13, 14, 15, 16}}); for (int i = 0; i < 16; i++) Assert.AreEqual(rowMajor[i], m[i]); m = new Matrix44F(new Matrix33F(1, 2, 3, 4, 5, 6, 7, 8, 9), new Vector3F(10, 11, 12)); Assert.AreEqual(new Matrix44F(1, 2, 3, 10, 4, 5, 6, 11, 7, 8, 9, 12, 0, 0, 0, 1), m); }
public void Determinant() { MatrixF m = new Matrix44F(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16).ToMatrixF(); Assert.IsTrue(Numeric.IsZero(m.Determinant)); m = new Matrix44F(1, 2, 3, 4, -3, 4, 5, 6, 2, -5, 7, 4, 10, 2, -3, 9).ToMatrixF(); Assert.AreEqual(1142, m.Determinant); }
/// <summary> /// Updates the projection matrix. /// </summary> private void Update() { // Let the derived class update the projection. _projection = ComputeProjection(); _projectionInverse = _projection.Inverse; _projectionNeedsToBeUpdated = false; }
public static void ExtractPlanes(Matrix44F projection, IList<Plane> planes, bool normalize) { // See "Fast Extraction of Viewing Frustum Planes from the World-View-Projection Matrix", // http://crazyjoke.free.fr/doc/3D/plane%20extraction.pdf. // Notes: The planes in the paper are given as (a, b, c, d), where (a, b, c) // is the normal and d is -DistanceToOrigin. The normals in the paper point // inside, but in our implementation the normals need to point outside! Vector3F normal; float distance; // Near plane normal.X = -projection.M20; normal.Y = -projection.M21; normal.Z = -projection.M22; distance = projection.M23; planes.Add(new Plane(normal, distance)); // Far plane normal.X = -projection.M30 + projection.M20; normal.Y = -projection.M31 + projection.M21; normal.Z = -projection.M32 + projection.M22; distance = projection.M33 - projection.M23; planes.Add(new Plane(normal, distance)); // Left plane normal.X = -projection.M30 - projection.M00; normal.Y = -projection.M31 - projection.M01; normal.Z = -projection.M32 - projection.M02; distance = projection.M33 + projection.M03; planes.Add(new Plane(normal, distance)); // Right plane normal.X = -projection.M30 + projection.M00; normal.Y = -projection.M31 + projection.M01; normal.Z = -projection.M32 + projection.M02; distance = projection.M33 - projection.M03; planes.Add(new Plane(normal, distance)); // Bottom plane normal.X = -projection.M30 - projection.M10; normal.Y = -projection.M31 - projection.M11; normal.Z = -projection.M32 - projection.M12; distance = projection.M33 + projection.M13; planes.Add(new Plane(normal, distance)); // Top plane normal.X = -projection.M30 + projection.M10; normal.Y = -projection.M31 + projection.M11; normal.Z = -projection.M32 + projection.M12; distance = projection.M33 - projection.M13; planes.Add(new Plane(normal, distance)); if (normalize) { for (int i = 0; i < planes.Count; i++) { try { var plane = planes[i]; plane.Normalize(); planes[i] = plane; } catch (DivideByZeroException) { if (i != 1) throw; throw new DivideByZeroException("Cannot normalize far plane of view frustum. " + "The near-far range of the projection is too large. " + "Try to increase the near distance or decrease the far distance."); } } } }
public void GetColumnException1() { Matrix44F m = new Matrix44F(rowMajor, MatrixOrder.RowMajor); m.GetColumn(-1); }
public void GetColumn() { Matrix44F m = new Matrix44F(rowMajor, MatrixOrder.RowMajor); Assert.AreEqual(new Vector4F(1.0f, 5.0f, 9.0f, 13.0f), m.GetColumn(0)); Assert.AreEqual(new Vector4F(2.0f, 6.0f, 10.0f, 14.0f), m.GetColumn(1)); Assert.AreEqual(new Vector4F(3.0f, 7.0f, 11.0f, 15.0f), m.GetColumn(2)); Assert.AreEqual(new Vector4F(4.0f, 8.0f, 12.0f, 16.0f), m.GetColumn(3)); }
/// <summary> /// Projects a position from world space into viewport. /// </summary> /// <param name="viewport">The viewport.</param> /// <param name="position">The position in view space.</param> /// <param name="projection">The projection matrix.</param> /// <returns> /// The position in the viewport: The x- and y-components define the pixel position /// in the range [0, viewport width/height]. The z-component defines the depth in clip space. /// </returns> internal static Vector3F ProjectToViewport(this Viewport viewport, Vector3F position, Matrix44F projection) { // Transform position to clip space. (TransformPosition() transforms the position // to clip space and performs the homogeneous divide.) Vector3F positionClip = projection.TransformPosition(position); Vector3F positionScreen = new Vector3F { X = (1f + positionClip.X) * 0.5f * viewport.Width, Y = (1f - positionClip.Y) * 0.5f * viewport.Height, Z = positionClip.Z, }; return positionScreen; }
public void DivisionOperator() { float s = 0.1234f; Matrix44F m = new Matrix44F(rowMajor, MatrixOrder.RowMajor); m = m / s; for (int i = 0; i < 16; i++) Assert.IsTrue(Numeric.AreEqual(rowMajor[i] / s, m[i])); }
public abstract void Set(Matrix44F projection);
public void Determinant() { Matrix44F m = new Matrix44F(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16); Assert.AreEqual(0, m.Determinant); m = new Matrix44F(1, 2, 3, 4, -3, 4, 5, 6, 2, -5, 7, 4, 10, 2, -3, 9); Assert.AreEqual(1142, m.Determinant); }
// OnUpdate() is called once per frame. protected override void OnUpdate(TimeSpan deltaTime) { if (!IsEnabled) return; // Reset camera position if <Home> is pressed. if (_inputService.IsPressed(Keys.Home, false)) { ResetPose(); } // Zoom control //TODO(matt) this needs lots of work! _zoomPercent += 0.001f * _inputService.MouseWheelDelta; _zoomPercent = MathHelper.Clamp<float>(_zoomPercent, 0.1f, 25); ResetProjection(); if (_inputService.IsDown(MouseButtons.Middle)) { var graphicsService = _services.GetInstance<IGraphicsService>(); var mousePos = -_inputService.MousePosition; if (_inputService.IsPressed(MouseButtons.Middle, false)) { originalCameraMat = CameraNode.PoseWorld.Inverse.ToMatrix44F(); originalCameraPos = CameraNode.PoseWorld.Position; mouseWorldPosOld = GraphicsHelper.Unproject(graphicsService.GraphicsDevice.Viewport, new Vector3F(mousePos.X, mousePos.Y, 0), CameraNode.Camera.Projection.ToMatrix44F(), originalCameraMat); } else { var worldPos = GraphicsHelper.Unproject(graphicsService.GraphicsDevice.Viewport, new Vector3F(mousePos.X, mousePos.Y, 0), CameraNode.Camera.Projection.ToMatrix44F(), originalCameraMat); CameraNode.PoseWorld = new Pose( originalCameraPos + new Vector3F(worldPos.X, worldPos.Y, 1) - new Vector3F(mouseWorldPosOld.X, mouseWorldPosOld.Y, 0), QuaternionF.Identity); } } }
public void DecomposeShouldFail() { Matrix44F matrix = new Matrix44F(); Vector3F scaleOfMatrix; QuaternionF rotationOfMatrix; Vector3F translationOfMatrix; bool result = matrix.Decompose(out scaleOfMatrix, out rotationOfMatrix, out translationOfMatrix); Assert.IsFalse(result); matrix = new Matrix44F(rowMajor, MatrixOrder.RowMajor); result = matrix.Decompose(out scaleOfMatrix, out rotationOfMatrix, out translationOfMatrix); Assert.IsFalse(result); }
public void Transposed() { Matrix44F m = new Matrix44F(rowMajor, MatrixOrder.RowMajor); Matrix44F mt = new Matrix44F(rowMajor, MatrixOrder.ColumnMajor); Assert.AreEqual(mt, m.Transposed); Assert.AreEqual(Matrix44F.Identity, Matrix44F.Identity.Transposed); }
/// <summary> /// Converts the specified distance to a view-normalized distance ("LOD distance"). /// </summary> /// <param name="distance">The 3D Euclidean distance between the object and the camera.</param> /// <param name="projection">The projection transformation.</param> /// <returns>The view-normalized distance.</returns> /// <inheritdoc cref="GetViewNormalizedDistance(DigitalRune.Graphics.SceneGraph.SceneNode,DigitalRune.Graphics.SceneGraph.CameraNode)"/> public static float GetViewNormalizedDistance(float distance, Matrix44F projection) { Debug.Assert(distance >= 0, "The distance should be greater than or equal to 0."); float yScale = Math.Abs(projection.M11); return distance / yScale; }
public void TransformNormal() { // Random matrix Matrix44F transform = new Matrix44F(1, 2, 3, 4, 2, 5, 8, 3, 7, 6, -1, 1, 0, 0, 0, 1); Vector3F p3 = new Vector3F(1.0f, 2.0f, 0.5f); Vector3F x3 = new Vector3F(-3.4f, 5.5f, -0.5f); Vector3F d = (x3 - p3); Vector3F n3 = d.Orthonormal1; Vector4F p4 = new Vector4F(p3.X, p3.Y, p3.Z, 1.0f); Vector4F x4 = new Vector4F(x3.X, x3.Y, x3.Z, 1.0f); Vector4F n4 = new Vector4F(n3.X, n3.Y, n3.Z, 0.0f); float planeEquation = Vector4F.Dot((x4 - p4), n4); Assert.IsTrue(Numeric.IsZero(planeEquation)); p4 = transform * p4; x4 = transform * x4; n3 = transform.TransformNormal(n3); n4 = new Vector4F(n3.X, n3.Y, n3.Z, 0.0f); planeEquation = Vector4F.Dot((x4 - p4), n4); Assert.IsTrue(Numeric.IsZero(planeEquation)); }
public void EqualityOperators() { Matrix44F m1 = new Matrix44F(rowMajor, MatrixOrder.RowMajor); Matrix44F m2 = new Matrix44F(rowMajor, MatrixOrder.RowMajor); Assert.IsTrue(m1 == m2); Assert.IsFalse(m1 != m2); for (int i = 0; i < 16; i++) { m2 = new Matrix44F(rowMajor, MatrixOrder.RowMajor); m2[i] += 0.1f; Assert.IsFalse(m1 == m2); Assert.IsTrue(m1 != m2); } }
private static void ComparePlanes(List<Plane> planes, Matrix44F viewProjection) { var viewProjectionInverse = viewProjection.Inverse; var nearPlane = new Plane( viewProjectionInverse.TransformPosition(new Vector3F(1, -1, 0)), viewProjectionInverse.TransformPosition(new Vector3F(1, 1, 0)), viewProjectionInverse.TransformPosition(new Vector3F(-1, 1, 0))); ComparePlanes(nearPlane, planes[0]); var farPlane = new Plane( viewProjectionInverse.TransformPosition(new Vector3F(1, 1, 1)), viewProjectionInverse.TransformPosition(new Vector3F(1, -1, 1)), viewProjectionInverse.TransformPosition(new Vector3F(-1, -1, 1))); ComparePlanes(farPlane, planes[1]); var leftPlane = new Plane( viewProjectionInverse.TransformPosition(new Vector3F(-1, -1, 0)), viewProjectionInverse.TransformPosition(new Vector3F(-1, 1, 1)), viewProjectionInverse.TransformPosition(new Vector3F(-1, -1, 1))); ComparePlanes(leftPlane, planes[2]); var rightPlane = new Plane( viewProjectionInverse.TransformPosition(new Vector3F(1, -1, 1)), viewProjectionInverse.TransformPosition(new Vector3F(1, 1, 1)), viewProjectionInverse.TransformPosition(new Vector3F(1, 1, 0))); ComparePlanes(rightPlane, planes[3]); var bottomPlane = new Plane( viewProjectionInverse.TransformPosition(new Vector3F(1, -1, 0)), viewProjectionInverse.TransformPosition(new Vector3F(-1, -1, 1)), viewProjectionInverse.TransformPosition(new Vector3F(1, -1, 1))); ComparePlanes(bottomPlane, planes[4]); var topPlane = new Plane( viewProjectionInverse.TransformPosition(new Vector3F(1, 1, 0)), viewProjectionInverse.TransformPosition(new Vector3F(1, 1, 1)), viewProjectionInverse.TransformPosition(new Vector3F(-1, 1, 1))); ComparePlanes(topPlane, planes[5]); }
/// <summary> /// Creates an orthographic projection from a 4x4 transformation matrix. /// </summary> /// <param name="matrix">The projection matrix.</param> /// <returns>The orthographic projection.</returns> public static OrthographicProjection FromMatrix(Matrix44F matrix) { var projection = new OrthographicProjection(); projection.Set(matrix); return projection; }