/* * Created by SharpDevelop. * User: OgreVorbis * Date: 1/1/2022 * Time: 9:19 PM * * This will render a cube(s) with OpenTK at a specific world positions and create an FPS style camera. * The OpenTK FPS camera sample has some bugs and isn't written in a straightforward way. * This will start you on a path of a Minecraft type game or anything else based on rendering lots of cubes. * You need OpenTK 3.3.1 and a reference to system drawing. */ using System; using OpenTK; using OpenTK.Graphics; using OpenTK.Graphics.OpenGL; using OpenTK.Input; namespace OpenTKTest { class Game : GameWindow { const float speed = 0.12f; const float sensitivity = 0.16f; float pitch = 0.0f; float yaw = -90.0f; bool firstMove = true; Vector2 lastPos; Vector3 position = new Vector3(0.0f, 0.0f, 5.0f); Vector3 front = new Vector3(0.0f, 0.0f, -2.0f); Vector3 up = new Vector3(0.0f, 2.0f, 0.0f); public Game() : base(800, 600, GraphicsMode.Default, "OpenTK Cube and Camera") { VSync = VSyncMode.On; } void drawCube(float x, float y, float z) { const float sizex = 0.5f; const float sizey = 0.5f; const float sizez = 0.5f; GL.Translate(-x, -y, -z); GL.Begin(PrimitiveType.Quads); GL.Color3(1.0, 1.0, 0.0); // FRONT GL.Vertex3(-sizex, -sizey, sizez); GL.Vertex3(sizex, -sizey, sizez); GL.Vertex3(sizex, sizey, sizez); GL.Vertex3(-sizex, sizey, sizez); // BACK GL.Vertex3(-sizex, -sizey, -sizez); GL.Vertex3(-sizex, sizey, -sizez); GL.Vertex3(sizex, sizey, -sizez); GL.Vertex3(sizex, -sizey, -sizez); GL.Color3(0.0, 1.0, 0.0); // LEFT GL.Vertex3(-sizex, -sizey, sizez); GL.Vertex3(-sizex, sizey, sizez); GL.Vertex3(-sizex, sizey, -sizez); GL.Vertex3(-sizex, -sizey, -sizez); // RIGHT GL.Vertex3(sizex, -sizey, -sizez); GL.Vertex3(sizex, sizey, -sizez); GL.Vertex3(sizex, sizey, sizez); GL.Vertex3(sizex, -sizey, sizez); //GL.Color3(1.0, 0.0, 1.0); // we test if we can use bytes here for later - yes we can GL.Color3((byte)255, (byte)0, (byte)255); // TOP GL.Vertex3(-sizex, sizey, sizez); GL.Vertex3(sizex, sizey, sizez); GL.Vertex3(sizex, sizey, -sizez); GL.Vertex3(-sizex, sizey, -sizez); // BOTTOM GL.Vertex3(-sizex, -sizey, sizez); GL.Vertex3(-sizex, -sizey, -sizez); GL.Vertex3(sizex, -sizey, -sizez); GL.Vertex3(sizex, -sizey, sizez); GL.End(); GL.Translate(x, y, z); } protected override void OnLoad(EventArgs e) { base.OnLoad(e); GL.ClearColor(0.1f, 0.2f, 0.5f, 0.0f); GL.Enable(EnableCap.DepthTest); CursorGrabbed = true; CursorVisible = false; } protected override void OnResize(EventArgs e) { base.OnResize(e); GL.Viewport(ClientRectangle.X, ClientRectangle.Y, ClientRectangle.Width, ClientRectangle.Height); Matrix4 projection = Matrix4.CreatePerspectiveFieldOfView((float)Math.PI / 4, Width / (float)Height, 1.0f, 64.0f); GL.MatrixMode(MatrixMode.Projection); GL.LoadMatrix(ref projection); } // MIGHT NOT NEED THIS FUNCTION protected override void OnMouseMove(MouseMoveEventArgs e) { if (Focused) // check to see if the window is focused { Mouse.SetPosition(X + Width / 2f, Y + Height / 2f); } base.OnMouseMove(e); } protected override void OnUpdateFrame(FrameEventArgs e) { base.OnUpdateFrame(e); if (!Focused) // check to see if the window is focused { return; } KeyboardState input = Keyboard.GetState(); MouseState mouse = Mouse.GetState(); // KEYBOARD MOVEMENT SECTION if (input.IsKeyDown(Key.W)) position += front * speed; //Forward if (input.IsKeyDown(Key.S)) position -= front * speed; //Backwards if (input.IsKeyDown(Key.A)) position -= Vector3.Normalize(Vector3.Cross(front, up)) * speed; //Left if (input.IsKeyDown(Key.D)) position += Vector3.Normalize(Vector3.Cross(front, up)) * speed; //Right if (input.IsKeyDown(Key.Space)) position += up * speed; //Up if (input.IsKeyDown(Key.LShift)) position -= up * speed; //Down if (input.IsKeyDown(Key.Escape)) { CursorGrabbed = false; CursorVisible = true; } // MOUSE MOVEMENT SECTION if (firstMove) { lastPos = new Vector2(mouse.X, mouse.Y); firstMove = false; } else { float deltaX = mouse.X - lastPos.X; float deltaY = mouse.Y - lastPos.Y; lastPos = new Vector2(mouse.X, mouse.Y); yaw += deltaX * sensitivity; pitch -= deltaY * sensitivity; if(pitch > 89.0f) pitch = 89.0f; else if(pitch < -89.0f) pitch = -89.0f; } front.X = (float)Math.Cos(MathHelper.DegreesToRadians(pitch)) * (float)Math.Cos(MathHelper.DegreesToRadians(yaw)); front.Y = (float)Math.Sin(MathHelper.DegreesToRadians(pitch)); front.Z = (float)Math.Cos(MathHelper.DegreesToRadians(pitch)) * (float)Math.Sin(MathHelper.DegreesToRadians(yaw)); front = Vector3.Normalize(front); } protected override void OnRenderFrame(FrameEventArgs e) { base.OnRenderFrame(e); GL.Clear(ClearBufferMask.ColorBufferBit | ClearBufferMask.DepthBufferBit); Matrix4 modelview = Matrix4.LookAt(position, position + front, up); GL.MatrixMode(MatrixMode.Modelview); GL.LoadMatrix(ref modelview); drawCube(0.0f, 0.0f, -2.0f); SwapBuffers(); } [STAThread] public static void Main(string[] args) { using (Game game = new Game()) { game.Run(60.0); } } } }