void Camera::Roll(float theta) { Matrix4 Rotation = Matrix4::Rotation(_look, theta); _up = Rotation.TransformPoint(_up); _right = Rotation.TransformPoint(_right); _look = Rotation.TransformPoint(_look); }
void SoftwareGraphicsDevice::Render(const Mesh &M) { //uses AliasRender to render the provided polygon. MeshVertex Polygon[10]; int i,i2,i2p1,ic=M.IndexCount(),LocalVC; const MeshVertex *V = M.Vertices(); const DWORD *I = M.Indices(); Clipper Clip; Clip.Init(float(Bmp.Width()-1),float(Bmp.Height()-1)); //prepare for clipping Matrix4 VTranslate = Matrix4::Translation(Vec3f(1.0f,1.0f,0.0f)); Matrix4 VScale = Matrix4::Scaling(Vec3f(Bmp.Width()/2.0f,Bmp.Height()/2.0f,1.0f)); Matrix4 Viewport = VTranslate * VScale; Matrix4 TotalViewport = Total * Viewport; //get the total transform for(i=0; i<ic; i+=3) { LocalVC = 3; Polygon[0] = V[I[i+0]]; Polygon[1] = V[I[i+1]]; Polygon[2] = V[I[i+2]]; //load the current triangle // // Transform into screen space // Polygon[0].Pos = TotalViewport.TransformPoint(Polygon[0].Pos); Polygon[1].Pos = TotalViewport.TransformPoint(Polygon[1].Pos); Polygon[2].Pos = TotalViewport.TransformPoint(Polygon[2].Pos); Clip.Clip(Polygon, LocalVC); //clip if(_Wireframe) { for(i2=0; i2<LocalVC; i2++) { i2p1 = i2 + 1; if(i2p1 == LocalVC) i2p1 = 0; //if we're in _Wireframe, draw lines representing the polygon if(Polygon[i2].Pos.z >= 0.0f && Polygon[i2].Pos.z <= 1.0f && Polygon[i2p1].Pos.z >= 0.0f && Polygon[i2p1].Pos.z <= 1.0f) PR.DrawLine(Bmp, int(Polygon[i2].Pos.x), int(Polygon[i2].Pos.y), int(Polygon[i2p1].Pos.x), int(Polygon[i2p1].Pos.y), Polygon[i2].Color); } } else { //if we're not in _Wireframe, draw the polygon directly PR.DrawPolygon(Bmp, Z, Polygon, LocalVC); } } }
void BaseMesh::LoadMeshList(const Vector< pair<const BaseMesh *, Matrix4> > &Meshes) { UINT NewVertexCount = 0, NewFaceCount = 0; for(UINT MeshIndex = 0; MeshIndex < Meshes.Length(); MeshIndex++) { const BaseMesh &CurMesh = *(Meshes[MeshIndex].first); NewVertexCount += CurMesh.VertexCount(); NewFaceCount += CurMesh.FaceCount(); } Allocate(NewVertexCount, NewFaceCount); UINT VertexBaseIndex = 0, IndexBaseIndex = 0; for(UINT MeshIndex = 0; MeshIndex < Meshes.Length(); MeshIndex++) { const BaseMesh &CurMesh = *(Meshes[MeshIndex].first); Matrix4 Transform = Meshes[MeshIndex].second; for(UINT VertexIndex = 0; VertexIndex < CurMesh.VertexCount(); VertexIndex++) { Vertices()[VertexBaseIndex + VertexIndex] = CurMesh.Vertices()[VertexIndex]; Vertices()[VertexBaseIndex + VertexIndex].Pos = Transform.TransformPoint(Vertices()[VertexBaseIndex + VertexIndex].Pos); } for(UINT FaceIndex = 0; FaceIndex < CurMesh.FaceCount(); FaceIndex++) { for(UINT LocalVertexIndex = 0; LocalVertexIndex < 3; LocalVertexIndex++) { Indices()[IndexBaseIndex + FaceIndex * 3 + LocalVertexIndex] = CurMesh.Indices()[FaceIndex * 3 + LocalVertexIndex] + VertexBaseIndex; } } VertexBaseIndex += CurMesh.VertexCount(); IndexBaseIndex += CurMesh.FaceCount() * 3; } }
bool M4TransformPointTest::DoTest() { Matrix4 Dummy; Dummy.TransformPoint(m_oVector, m_fAngle, m_fScale, m_cAxis, m_oTransVector); cout<< "\n---------------M4TransformPointTest---------------\n"; return (m_oVector == m_oResult); }
void BaseMesh::CreateViewPlane(float EyeDist, UINT slices, MatrixController &MC) { Matrix4 Perspective = MC.Perspective, PInverse; PInverse = Perspective.Inverse(); Vec3f PerspectiveCoord(0.0f, 0.0f, EyeDist); PerspectiveCoord = Perspective.TransformPoint(PerspectiveCoord); //get the top-left coord in persp. space PerspectiveCoord.x = 1.0f; PerspectiveCoord.y = -1.0f; PerspectiveCoord = PInverse.TransformPoint(PerspectiveCoord); //get the bottom-right coord in persp. space CreatePlane(2.0f, slices, slices); //create the X-Y plane Matrix4 Scale = Matrix4::Scaling(Vec3f(PerspectiveCoord.x, PerspectiveCoord.y, 1.0f)); //scale it appropriately, Matrix4 Translate = Matrix4::Translation(Vec3f(0.0f,0.0f,PerspectiveCoord.z)); //translate it away from the eye, Matrix4 VInverse = MC.View.Inverse(); //we need to transform our mesh and we want to fact the view and world transforms in Matrix4 WInverse = MC.World.Inverse(); // // Translate and scale, then go into object space by multiplying through the inverse of view/world. // ApplyMatrix(Translate * Scale * VInverse * WInverse); }
void Indicator::GetCameraLine(const Matrix4 &Perspective, const Camera &C, float x, float y, Vec3f &P1Out, Vec3f &P2Out) { Matrix4 Total = (C.Matrix() * Perspective).Inverse(); //the perspective -> view transform Vec3f P1(x * 2.0f - 1.0f, y * 2.0f - 1.0f, 0.0f), P2; P2 = Vec3f(P1.x, P1.y, 1.0f); //P1 and P2 are the segment corresponding to (x, y) on the perpsective cube P1Out = Total.TransformPoint(P1); P2Out = Total.TransformPoint(P2); }
void BaseMesh::ApplyMatrix(const Matrix4 &M) { UINT vc = VertexCount(); MeshVertex *V = Vertices(); for(UINT i = 0; i < vc; i++) { V[i].Pos = M.TransformPoint(V[i].Pos); V[i].Normal = M.TransformNormal(V[i].Normal); } }
void FluidApplication::ProcessUserInput(float secondsBetweenFrames) { const float cameraMoveSpeed = 0.1f * secondsBetweenFrames; Vector3 pan = { 0.0f, 0.0f, 0.0f }; // Move camera forward and backward using the mouse wheel. pan.z = DirectInput()->MouseMoveZ(); // Move camera sideways if the right button is down. if (DirectInput()->MouseDown(1)) { pan.x = -DirectInput()->MouseMoveX(); pan.y = DirectInput()->MouseMoveY(); } // Update camera position. _renderer->PanCamera(pan * cameraMoveSpeed); static Vector3 p0 = {0.0f, 0.0f, 0.0f}; // Records "mouse-pressed" location. static Vector3 p1 = {0.0f, 0.0f, 0.0f}; // Records "mouse-release" location. if (DirectInput()->MousePressed(0)) { p0 = MousePosWindowCoords(); } if (DirectInput()->MouseReleased(0)) { p1 = MousePosWindowCoords(); const Sizei size = GetClientSize(); const Matrix4 window2ndc = NDCToWindowMatrix(0, 0, size.width, size.height).Inverse3x4(); // Get coord in texture space const Vector2 p0tex = _renderer->CoordToTextureSpace(window2ndc.TransformPoint(p0).XY()); const Vector2 p1tex = _renderer->CoordToTextureSpace(window2ndc.TransformPoint(p1).XY()); const Vector2 dir = p1tex - p0tex; // Add the impulse to the fluid simulation. Fluid::Pulse pulse; pulse.position = p0tex; pulse.direction = dir; pulse.sigma = kFluidSplatSigma; pulse.amplitude = kFluidSplatAmplitude; //The pulse will be replaced, no matter if it has been processed or not. _fluid.AddForces(pulse); } // Switch between render modes. if (DirectInput()->KeyPressed(DIK_1)) { _renderer->SetRenderMode(FluidRenderer::kVelocitiesAsColors); } else if (DirectInput()->KeyPressed(DIK_2)) { _renderer->SetRenderMode(FluidRenderer::kVelocitiesAsLines); } }