massive refactor
This commit is contained in:
1 parent
26c0f433ae
commit
e71a1a9b0b
14 files changed
+442
-275
No files matched your search
@@ -1,149 +0,0 @@
|
|||||||
package org.example;
|
|
||||||
|
|
||||||
import org.joml.*;
|
|
||||||
import org.lwjgl.*;
|
|
||||||
import org.lwjgl.Version;
|
|
||||||
import org.lwjgl.glfw.*;
|
|
||||||
import org.lwjgl.opengl.*;
|
|
||||||
import org.lwjgl.system.*;
|
|
||||||
|
|
||||||
import java.lang.Math;
|
|
||||||
import java.nio.*;
|
|
||||||
import java.io.*;
|
|
||||||
import java.text.MessageFormat;
|
|
||||||
|
|
||||||
import static org.lwjgl.glfw.Callbacks.*;
|
|
||||||
import static org.lwjgl.glfw.GLFW.*;
|
|
||||||
import static org.lwjgl.opengl.GL11.*;
|
|
||||||
import static org.lwjgl.opengl.GL15.*;
|
|
||||||
import static org.lwjgl.opengl.GL20.*;
|
|
||||||
import static org.lwjgl.opengl.GL30.*;
|
|
||||||
import static org.lwjgl.system.MemoryStack.*;
|
|
||||||
import static org.lwjgl.system.MemoryUtil.*;
|
|
||||||
|
|
||||||
import com.mokiat.data.front.parser.*;
|
|
||||||
import org.lwjgl.system.MemoryStack;
|
|
||||||
|
|
||||||
public class Game
|
|
||||||
{
|
|
||||||
public static final float Z_FAR = 1000.0f;
|
|
||||||
public static final float Z_NEAR = 0.1f;
|
|
||||||
public static final float FOV = (float) Math.toRadians(90.0f);
|
|
||||||
private long window;
|
|
||||||
private Matrix4f projection_matrix;
|
|
||||||
|
|
||||||
public void run()
|
|
||||||
{
|
|
||||||
System.out.println("Running LWJGL Version " + Version.getVersion() + ".");
|
|
||||||
|
|
||||||
init();
|
|
||||||
loop();
|
|
||||||
|
|
||||||
// Free the window callbacks and destroy the window
|
|
||||||
glfwFreeCallbacks(window);
|
|
||||||
glfwDestroyWindow(window);
|
|
||||||
|
|
||||||
// Terminate GLFW and free the error callback
|
|
||||||
glfwTerminate();
|
|
||||||
glfwSetErrorCallback(null).free();
|
|
||||||
}
|
|
||||||
|
|
||||||
public void init()
|
|
||||||
{
|
|
||||||
GLFWErrorCallback.createPrint(System.err).set();
|
|
||||||
|
|
||||||
if (!glfwInit())
|
|
||||||
throw new IllegalStateException("Unable to Initialize GLFW");
|
|
||||||
|
|
||||||
// Configure GLFW
|
|
||||||
glfwDefaultWindowHints(); // optional, the current window hints are already the default
|
|
||||||
glfwWindowHint(GLFW_VISIBLE, GLFW_FALSE); // the window will stay hidden after creation
|
|
||||||
glfwWindowHint(GLFW_RESIZABLE, GLFW_TRUE); // the window will be resizable
|
|
||||||
|
|
||||||
// Create the window
|
|
||||||
window = glfwCreateWindow(300, 300, "Hello World!", NULL, NULL);
|
|
||||||
if ( window == NULL )
|
|
||||||
throw new RuntimeException("Failed to create the GLFW window");
|
|
||||||
|
|
||||||
// Setup a key callback. It will be called every time a key is pressed, repeated or released.
|
|
||||||
glfwSetKeyCallback(window, (window, key, scancode, action, mods) -> {
|
|
||||||
if ( key == GLFW_KEY_ESCAPE && action == GLFW_RELEASE )
|
|
||||||
glfwSetWindowShouldClose(window, true); // We will detect this in the rendering loop
|
|
||||||
});
|
|
||||||
|
|
||||||
// Get the thread stack and push a new frame
|
|
||||||
try ( MemoryStack stack = stackPush() ) {
|
|
||||||
IntBuffer pWidth = stack.mallocInt(1); // int*
|
|
||||||
IntBuffer pHeight = stack.mallocInt(1); // int*
|
|
||||||
|
|
||||||
// Get the window size passed to glfwCreateWindow
|
|
||||||
glfwGetWindowSize(window, pWidth, pHeight);
|
|
||||||
|
|
||||||
// Get the resolution of the primary monitor
|
|
||||||
GLFWVidMode vidmode = glfwGetVideoMode(glfwGetPrimaryMonitor());
|
|
||||||
|
|
||||||
// Center the window
|
|
||||||
glfwSetWindowPos(
|
|
||||||
window,
|
|
||||||
(vidmode.width() - pWidth.get(0)) / 2,
|
|
||||||
(vidmode.height() - pHeight.get(0)) / 2
|
|
||||||
);
|
|
||||||
} // the stack frame is popped automatically
|
|
||||||
|
|
||||||
// Make the OpenGL context current
|
|
||||||
glfwMakeContextCurrent(window);
|
|
||||||
// Enable v-sync
|
|
||||||
glfwSwapInterval(1);
|
|
||||||
|
|
||||||
// Make the window visible
|
|
||||||
glfwShowWindow(window);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void loop()
|
|
||||||
{
|
|
||||||
// Setup world
|
|
||||||
World world = new World();
|
|
||||||
|
|
||||||
// Do open gl stuff
|
|
||||||
GL.createCapabilities();
|
|
||||||
glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
|
|
||||||
|
|
||||||
// Add stuff to world
|
|
||||||
world.addEntity(new Entity("/objs/cube.obj", "/shaders/shader.frag", "/shaders/shader.vert"));
|
|
||||||
|
|
||||||
// Calculate Perspective Matrix
|
|
||||||
int w, h;
|
|
||||||
glfwGetWindowSize(window, w, h);
|
|
||||||
float aspect_ratio = (float) ;
|
|
||||||
this.projection_matrix = new Matrix4f().perspective(FOV, )
|
|
||||||
|
|
||||||
// Main loop or something
|
|
||||||
while ( !glfwWindowShouldClose(window) )
|
|
||||||
{
|
|
||||||
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
|
||||||
|
|
||||||
glfwSwapBuffers(window);
|
|
||||||
|
|
||||||
for (Entity entity : world.entities)
|
|
||||||
render(entity);
|
|
||||||
|
|
||||||
glfwPollEvents();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
public void render(Entity entity) {
|
|
||||||
entity.shader.bind();
|
|
||||||
|
|
||||||
glBindVertexArray(entity.mesh.vao_id);
|
|
||||||
glEnableVertexAttribArray(0);
|
|
||||||
glEnableVertexAttribArray(1);
|
|
||||||
glDrawElements(GL_TRIANGLES, entity.mesh.vertex_count, GL_UNSIGNED_INT, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
public static void main(String[] args)
|
|
||||||
{
|
|
||||||
new Game().run();
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
@@ -1,24 +0,0 @@
|
|||||||
package org.example;
|
|
||||||
|
|
||||||
|
|
||||||
import org.lwjgl.glfw.*;
|
|
||||||
import org.lwjgl.system.MemoryUtil;
|
|
||||||
|
|
||||||
import java.util.concurrent.Callable;
|
|
||||||
|
|
||||||
import static org.lwjgl.glfw.Callbacks.glfwFreeCallbacks;
|
|
||||||
import static org.lwjgl.glfw.GLFW.*;
|
|
||||||
import static org.lwjgl.opengl.GL11.*;
|
|
||||||
import static org.lwjgl.system.MemoryUtil.NULL;
|
|
||||||
|
|
||||||
public class Window {
|
|
||||||
public long window_handle;
|
|
||||||
|
|
||||||
public int height;
|
|
||||||
public int width;
|
|
||||||
private Callable<Void> resize_func;
|
|
||||||
|
|
||||||
public Window(String title, Callable<Void> resize_func) {
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -0,0 +1,95 @@
|
|||||||
|
package org.xfe.engine;
|
||||||
|
|
||||||
|
import org.joml.*;
|
||||||
|
|
||||||
|
import java.lang.Math;
|
||||||
|
|
||||||
|
public class Engine
|
||||||
|
{
|
||||||
|
public static final int TARGET_UPS = 30;
|
||||||
|
private final GameLogic gameLogic;
|
||||||
|
private final Render render;
|
||||||
|
private final Window window;
|
||||||
|
private final World world;
|
||||||
|
private int target_fps;
|
||||||
|
private int target_ups;
|
||||||
|
private boolean running;
|
||||||
|
|
||||||
|
public static final float Z_FAR = 1000.0f;
|
||||||
|
public static final float Z_NEAR = 0.1f;
|
||||||
|
public static final float FOV = (float) Math.toRadians(90.0f);
|
||||||
|
|
||||||
|
public Engine(String window_title, Window.WindowOptions opts, GameLogic gameLogic) {
|
||||||
|
window = new Window(window_title, opts, () -> {
|
||||||
|
resize();
|
||||||
|
return null;
|
||||||
|
});
|
||||||
|
target_fps = opts.fps;
|
||||||
|
target_ups = opts.ups;
|
||||||
|
|
||||||
|
this.gameLogic = gameLogic;
|
||||||
|
this.render = new Render();
|
||||||
|
this.world = new World();
|
||||||
|
|
||||||
|
gameLogic.init(window, world, render);
|
||||||
|
|
||||||
|
this.running = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void cleanup() {
|
||||||
|
this.gameLogic.cleanup();
|
||||||
|
this.render.cleanup();
|
||||||
|
this.world.cleanup();
|
||||||
|
this.window.cleanup();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void resize() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private void run() {
|
||||||
|
long initialTime = System.currentTimeMillis();
|
||||||
|
float timeU = 1000.0f / target_ups;
|
||||||
|
float timeR = target_fps > 0 ? 1000.0f / target_fps : 0;
|
||||||
|
float deltaUpdate = 0;
|
||||||
|
float deltaFps = 0;
|
||||||
|
|
||||||
|
long updateTime = initialTime;
|
||||||
|
while (running && !window.windowShouldClose()) {
|
||||||
|
window.pollEvents();
|
||||||
|
|
||||||
|
long now = System.currentTimeMillis();
|
||||||
|
deltaUpdate += (now - initialTime) / timeU;
|
||||||
|
deltaFps += (now - initialTime) / timeR;
|
||||||
|
|
||||||
|
if (target_fps <= 0 || deltaFps >= 1) {
|
||||||
|
gameLogic.input(window, world, now - initialTime);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (deltaUpdate >= 1) {
|
||||||
|
long diffTimeMillis = now - updateTime;
|
||||||
|
gameLogic.update(window, world, diffTimeMillis);
|
||||||
|
updateTime = now;
|
||||||
|
deltaUpdate--;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (target_fps <= 0 || deltaFps >= 1) {
|
||||||
|
render.render(window, world);
|
||||||
|
deltaFps--;
|
||||||
|
window.update();
|
||||||
|
}
|
||||||
|
initialTime = now;
|
||||||
|
}
|
||||||
|
|
||||||
|
cleanup();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void start() {
|
||||||
|
running = true;
|
||||||
|
run();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void stop() {
|
||||||
|
running = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,13 +1,5 @@
|
|||||||
package org.example;
|
package org.xfe.engine;
|
||||||
|
|
||||||
import com.mokiat.data.front.parser.IOBJParser;
|
|
||||||
import com.mokiat.data.front.parser.OBJModel;
|
|
||||||
import com.mokiat.data.front.parser.OBJParser;
|
|
||||||
|
|
||||||
import java.io.File;
|
|
||||||
import java.io.FileNotFoundException;
|
|
||||||
import java.io.InputStream;
|
|
||||||
import java.text.MessageFormat;
|
|
||||||
import java.util.Scanner;
|
import java.util.Scanner;
|
||||||
|
|
||||||
public class Entity
|
public class Entity
|
||||||
@@ -44,5 +36,19 @@ public class Entity
|
|||||||
System.out.println("ERROR Initializing the fragment shader");
|
System.out.println("ERROR Initializing the fragment shader");
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
shader.link();
|
||||||
|
} catch (Exception e) {
|
||||||
|
System.out.println("Error linking shader program");
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
try {
|
||||||
|
shader.createUniform("projection");
|
||||||
|
} catch (Exception e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,11 @@
|
|||||||
|
package org.xfe.engine;
|
||||||
|
|
||||||
|
public interface GameLogic {
|
||||||
|
void cleanup();
|
||||||
|
|
||||||
|
void init(Window window, World world, Render render);
|
||||||
|
|
||||||
|
void input(Window window, World world, long diffTimeMillis);
|
||||||
|
|
||||||
|
void update(Window window, World world, long diffTimeMillis);
|
||||||
|
}
|
||||||
@@ -0,0 +1,17 @@
|
|||||||
|
package org.xfe.engine;
|
||||||
|
|
||||||
|
import org.joml.Vector3f;
|
||||||
|
|
||||||
|
public class Light {
|
||||||
|
Vector3f position;
|
||||||
|
|
||||||
|
float power;
|
||||||
|
|
||||||
|
Vector3f color;
|
||||||
|
|
||||||
|
public Light(Vector3f position, float power, Vector3f color) {
|
||||||
|
this.position = position;
|
||||||
|
this.power = power;
|
||||||
|
this.color = color;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,11 +1,13 @@
|
|||||||
package org.example;
|
package org.xfe.engine;
|
||||||
|
|
||||||
import org.apache.commons.lang3.ArrayUtils;
|
import org.apache.commons.lang3.ArrayUtils;
|
||||||
import org.lwjgl.system.MemoryUtil;
|
import org.lwjgl.system.MemoryUtil;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
import java.io.FileNotFoundException;
|
import java.io.FileNotFoundException;
|
||||||
|
import java.io.InputStream;
|
||||||
import java.nio.FloatBuffer;
|
import java.nio.FloatBuffer;
|
||||||
|
import java.nio.IntBuffer;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Scanner;
|
import java.util.Scanner;
|
||||||
|
|
||||||
@@ -19,6 +21,7 @@ public class Mesh {
|
|||||||
public int vertex_count;
|
public int vertex_count;
|
||||||
public int vao_id;
|
public int vao_id;
|
||||||
public int vbo_id;
|
public int vbo_id;
|
||||||
|
public int ebo_id;
|
||||||
|
|
||||||
Float[] vertices;
|
Float[] vertices;
|
||||||
Float[] normals;
|
Float[] normals;
|
||||||
@@ -38,7 +41,7 @@ public class Mesh {
|
|||||||
ArrayList<Integer> temp_normal_indices = new ArrayList<>();
|
ArrayList<Integer> temp_normal_indices = new ArrayList<>();
|
||||||
|
|
||||||
Scanner scanner;
|
Scanner scanner;
|
||||||
File obj;
|
InputStream obj;
|
||||||
|
|
||||||
String line;
|
String line;
|
||||||
String[] face_data_temp;
|
String[] face_data_temp;
|
||||||
@@ -47,9 +50,9 @@ public class Mesh {
|
|||||||
|
|
||||||
// Try to open the file
|
// Try to open the file
|
||||||
try {
|
try {
|
||||||
obj = new File(file_path);
|
obj = this.getClass().getResourceAsStream(file_path);
|
||||||
scanner = new Scanner(obj);
|
scanner = new Scanner(obj);
|
||||||
} catch (FileNotFoundException e) {
|
} catch (Exception e) {
|
||||||
System.out.println("ERROR: OBJ File \"" + file_path + "\" not found.");
|
System.out.println("ERROR: OBJ File \"" + file_path + "\" not found.");
|
||||||
e.printStackTrace();
|
e.printStackTrace();
|
||||||
return;
|
return;
|
||||||
@@ -98,11 +101,13 @@ public class Mesh {
|
|||||||
FloatBuffer vertices_buffer = null;
|
FloatBuffer vertices_buffer = null;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|
||||||
|
// Bind our vertices into the VBO
|
||||||
vertices_buffer = MemoryUtil.memAllocFloat(this.vertices.length);
|
vertices_buffer = MemoryUtil.memAllocFloat(this.vertices.length);
|
||||||
vertex_count = this.vertices.length / 3;
|
vertex_count = this.vertices.length / 3;
|
||||||
|
|
||||||
// Convert from our object list to the primitive float array
|
// Convert from our object list to the primitive float array
|
||||||
vertices_buffer.put(ArrayUtils.toPrimitive(this.vertices)).flip();
|
vertices_buffer.put(ArrayUtils.toPrimitive(this.vertices));
|
||||||
|
|
||||||
this.vao_id = glGenVertexArrays();
|
this.vao_id = glGenVertexArrays();
|
||||||
glBindVertexArray(this.vao_id);
|
glBindVertexArray(this.vao_id);
|
||||||
@@ -112,6 +117,18 @@ public class Mesh {
|
|||||||
glBufferData(GL_ARRAY_BUFFER, vertices_buffer, GL_STATIC_DRAW);
|
glBufferData(GL_ARRAY_BUFFER, vertices_buffer, GL_STATIC_DRAW);
|
||||||
glVertexAttribPointer(0, 3, GL_FLOAT, false, 0, 0);
|
glVertexAttribPointer(0, 3, GL_FLOAT, false, 0, 0);
|
||||||
|
|
||||||
|
// Bind indices in EBO
|
||||||
|
if (this.vertice_indices.length > 0)
|
||||||
|
{
|
||||||
|
// TODO : @0x01fe probably should free this (memory leaks are like bad or smthng)
|
||||||
|
IntBuffer indice_buffer = MemoryUtil.memAllocInt(vertice_indices.length);
|
||||||
|
indice_buffer.put(ArrayUtils.toPrimitive(vertice_indices));
|
||||||
|
|
||||||
|
ebo_id = glGenBuffers();
|
||||||
|
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, ebo_id);
|
||||||
|
glBufferData(GL_ELEMENT_ARRAY_BUFFER, indice_buffer, GL_STATIC_DRAW);
|
||||||
|
}
|
||||||
|
|
||||||
glBindBuffer(GL_ARRAY_BUFFER, 0);
|
glBindBuffer(GL_ARRAY_BUFFER, 0);
|
||||||
} finally {
|
} finally {
|
||||||
if (vertices_buffer != null) {
|
if (vertices_buffer != null) {
|
||||||
@@ -0,0 +1,50 @@
|
|||||||
|
package org.xfe.engine;
|
||||||
|
|
||||||
|
import org.joml.Matrix4f;
|
||||||
|
import org.joml.Vector3f;
|
||||||
|
import org.lwjgl.opengl.GL;
|
||||||
|
import static org.lwjgl.glfw.GLFW.*;
|
||||||
|
import static org.lwjgl.opengl.GL11.*;
|
||||||
|
import static org.lwjgl.opengl.GL15.*;
|
||||||
|
import static org.lwjgl.opengl.GL20.*;
|
||||||
|
import static org.lwjgl.opengl.GL30.*;
|
||||||
|
|
||||||
|
public class Render {
|
||||||
|
|
||||||
|
private Matrix4f projection_matrix;
|
||||||
|
public Render() {
|
||||||
|
GL.createCapabilities();
|
||||||
|
}
|
||||||
|
|
||||||
|
public void cleanup() {
|
||||||
|
// Nothing to be done here yet
|
||||||
|
}
|
||||||
|
|
||||||
|
public void render(Window window, World world) {
|
||||||
|
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
|
||||||
|
|
||||||
|
glfwSwapBuffers(window.getWindowHandle());
|
||||||
|
|
||||||
|
float aspect_ratio = (float) window.getWidth() / window.getHeight();
|
||||||
|
projection_matrix = new Matrix4f().perspective(Engine.FOV, aspect_ratio, Engine.Z_FAR, Engine.Z_NEAR);
|
||||||
|
|
||||||
|
for (Entity entity : world.entities) {
|
||||||
|
entity.shader.bind();
|
||||||
|
|
||||||
|
entity.shader.setUniform("projection", projection_matrix);
|
||||||
|
// entity.shader.setUniform("model", new Matrix4f().identity());
|
||||||
|
// entity.shader.setUniform("view", new Matrix4f().identity());
|
||||||
|
// entity.shader.setUniform("lightPos", world.lights.get(0).position);
|
||||||
|
// entity.shader.setUniform("light_power", world.lights.get(0).power);
|
||||||
|
// entity.shader.setUniform("lightColor", world.lights.get(0).color);
|
||||||
|
// entity.shader.setUniform("objectColor", new Vector3f(1.0f, 1.0f, 1.0f));
|
||||||
|
// entity.shader.setUniform("viewPos", new Vector3f(0.0f, 0.0f, 0.0f));
|
||||||
|
|
||||||
|
|
||||||
|
glBindVertexArray(entity.mesh.ebo_id);
|
||||||
|
glEnableVertexAttribArray(0);
|
||||||
|
// glEnableVertexAttribArray(1);
|
||||||
|
glDrawElements(GL_TRIANGLES, entity.mesh.vertice_indices.length, GL_UNSIGNED_INT, 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
+33
-41
@@ -1,4 +1,12 @@
|
|||||||
package org.example;
|
package org.xfe.engine;
|
||||||
|
|
||||||
|
import org.joml.Matrix4f;
|
||||||
|
import org.joml.Vector3f;
|
||||||
|
import org.lwjgl.system.MemoryStack;
|
||||||
|
|
||||||
|
import java.nio.FloatBuffer;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
import static org.lwjgl.opengl.GL20.*;
|
import static org.lwjgl.opengl.GL20.*;
|
||||||
|
|
||||||
@@ -6,11 +14,14 @@ public class ShaderProgram {
|
|||||||
|
|
||||||
private final int programId;
|
private final int programId;
|
||||||
|
|
||||||
|
private final Map<String, Integer> uniforms;
|
||||||
|
|
||||||
private int vertexShaderId;
|
private int vertexShaderId;
|
||||||
|
|
||||||
private int fragmentShaderId;
|
private int fragmentShaderId;
|
||||||
|
|
||||||
public ShaderProgram() throws Exception {
|
public ShaderProgram() throws Exception {
|
||||||
|
uniforms = new HashMap<>();
|
||||||
programId = glCreateProgram();
|
programId = glCreateProgram();
|
||||||
if (programId == 0) {
|
if (programId == 0) {
|
||||||
throw new Exception("Could not create Shader");
|
throw new Exception("Could not create Shader");
|
||||||
@@ -79,51 +90,32 @@ public class ShaderProgram {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Set stuff
|
// Set stuff
|
||||||
public void setFloat(String name, float value) {
|
public void createUniform(String uniform_name) throws Exception {
|
||||||
glUniform1f(glGetUniformLocation(programId, name), value);
|
int uniform_location = glGetUniformLocation(this.programId, uniform_name);
|
||||||
|
|
||||||
|
if (uniform_location < 0)
|
||||||
|
throw new Exception("Could not find uniform: " + uniform_name);
|
||||||
|
uniforms.put(uniform_name, uniform_location);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setBool(String name, boolean value) {
|
public void setUniform(String uniform_name, Matrix4f value) {
|
||||||
glUniform1i(glGetUniformLocation(programId, name), value ? 1 : 0);
|
// Dump the matrix into a float buffer
|
||||||
|
try (MemoryStack stack = MemoryStack.stackPush()) {
|
||||||
|
FloatBuffer floatBuffer = stack.mallocFloat(16);
|
||||||
|
value.get(floatBuffer);
|
||||||
|
glUniformMatrix4fv(uniforms.get(uniform_name), false, floatBuffer);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setInt(String name, int value) {
|
public void setUniform(String uniform_name, float value) {
|
||||||
glUniform1i(glGetUniformLocation(programId, name), value);
|
glUniform1f(uniforms.get(uniform_name), value);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setVec2(String name, float[] value) {
|
public void setUniform(String uniform_name, Vector3f value) {
|
||||||
glUniform2fv(glGetUniformLocation(programId, name), value);
|
try (MemoryStack stack = MemoryStack.stackPush()) {
|
||||||
}
|
FloatBuffer floatBuffer = stack.mallocFloat(3);
|
||||||
|
value.get(floatBuffer);
|
||||||
public void setVec2(String name, float x, float y) {
|
glUniform3fv(uniforms.get(uniform_name), floatBuffer);
|
||||||
glUniform2f(glGetUniformLocation(programId, name), x, y);
|
}
|
||||||
}
|
|
||||||
|
|
||||||
public void setVec3(String name, float[] value) {
|
|
||||||
glUniform3fv(glGetUniformLocation(programId, name), value);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setVec3(String name, float x, float y, float z) {
|
|
||||||
glUniform3f(glGetUniformLocation(programId, name), x, y, z);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setVec4(String name, float[] value) {
|
|
||||||
glUniform4fv(glGetUniformLocation(programId, name), value);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setVec4(String name, float x, float y, float z, float w) {
|
|
||||||
glUniform4f(glGetUniformLocation(programId, name), x, y, z, w);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setMat2(String name, float[] mat) {
|
|
||||||
glUniformMatrix2fv(glGetUniformLocation(programId, name), false, mat);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setMat3(String name, float[] mat) {
|
|
||||||
glUniformMatrix3fv(glGetUniformLocation(programId, name), false, mat);
|
|
||||||
}
|
|
||||||
|
|
||||||
public void setMat4(String name, float[] mat) {
|
|
||||||
glUniformMatrix4fv(glGetUniformLocation(programId, name), false, mat);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,137 @@
|
|||||||
|
package org.xfe.engine;
|
||||||
|
|
||||||
|
import org.lwjgl.glfw.*;
|
||||||
|
|
||||||
|
import java.util.concurrent.Callable;
|
||||||
|
|
||||||
|
import static org.lwjgl.glfw.Callbacks.glfwFreeCallbacks;
|
||||||
|
import static org.lwjgl.glfw.GLFW.*;
|
||||||
|
import static org.lwjgl.opengl.GL11.*;
|
||||||
|
import static org.lwjgl.system.MemoryUtil.NULL;
|
||||||
|
|
||||||
|
public class Window {
|
||||||
|
|
||||||
|
private final long windowHandle;
|
||||||
|
private int height;
|
||||||
|
private Callable<Void> resizeFunc;
|
||||||
|
private int width;
|
||||||
|
|
||||||
|
public Window(String title, WindowOptions opts, Callable<Void> resizeFunc) {
|
||||||
|
this.resizeFunc = resizeFunc;
|
||||||
|
if (!glfwInit()) {
|
||||||
|
throw new IllegalStateException("Unable to initialize GLFW");
|
||||||
|
}
|
||||||
|
|
||||||
|
glfwDefaultWindowHints();
|
||||||
|
glfwWindowHint(GLFW_VISIBLE, GL_FALSE);
|
||||||
|
glfwWindowHint(GLFW_RESIZABLE, GL_TRUE);
|
||||||
|
|
||||||
|
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
|
||||||
|
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
|
||||||
|
if (opts.compatibleProfile) {
|
||||||
|
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_COMPAT_PROFILE);
|
||||||
|
} else {
|
||||||
|
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
|
||||||
|
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (opts.width > 0 && opts.height > 0) {
|
||||||
|
this.width = opts.width;
|
||||||
|
this.height = opts.height;
|
||||||
|
} else {
|
||||||
|
glfwWindowHint(GLFW_MAXIMIZED, GLFW_TRUE);
|
||||||
|
GLFWVidMode vidMode = glfwGetVideoMode(glfwGetPrimaryMonitor());
|
||||||
|
width = vidMode.width();
|
||||||
|
height = vidMode.height();
|
||||||
|
}
|
||||||
|
|
||||||
|
windowHandle = glfwCreateWindow(width, height, title, NULL, NULL);
|
||||||
|
if (windowHandle == NULL) {
|
||||||
|
throw new RuntimeException("Failed to create the GLFW window");
|
||||||
|
}
|
||||||
|
|
||||||
|
glfwSetFramebufferSizeCallback(windowHandle, (window, w, h) -> resized(w, h));
|
||||||
|
|
||||||
|
glfwSetKeyCallback(windowHandle, (window, key, scancode, action, mods) -> {
|
||||||
|
keyCallBack(key, action);
|
||||||
|
});
|
||||||
|
|
||||||
|
glfwMakeContextCurrent(windowHandle);
|
||||||
|
|
||||||
|
if (opts.fps > 0) {
|
||||||
|
glfwSwapInterval(0);
|
||||||
|
} else {
|
||||||
|
glfwSwapInterval(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
glfwShowWindow(windowHandle);
|
||||||
|
|
||||||
|
int[] arrWidth = new int[1];
|
||||||
|
int[] arrHeight = new int[1];
|
||||||
|
glfwGetFramebufferSize(windowHandle, arrWidth, arrHeight);
|
||||||
|
width = arrWidth[0];
|
||||||
|
height = arrHeight[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
public void cleanup() {
|
||||||
|
glfwFreeCallbacks(windowHandle);
|
||||||
|
glfwDestroyWindow(windowHandle);
|
||||||
|
glfwTerminate();
|
||||||
|
GLFWErrorCallback callback = glfwSetErrorCallback(null);
|
||||||
|
if (callback != null) {
|
||||||
|
callback.free();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getHeight() {
|
||||||
|
return height;
|
||||||
|
}
|
||||||
|
|
||||||
|
public int getWidth() {
|
||||||
|
return width;
|
||||||
|
}
|
||||||
|
|
||||||
|
public long getWindowHandle() {
|
||||||
|
return windowHandle;
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean isKeyPressed(int keyCode) {
|
||||||
|
return glfwGetKey(windowHandle, keyCode) == GLFW_PRESS;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void keyCallBack(int key, int action) {
|
||||||
|
if (key == GLFW_KEY_ESCAPE && action == GLFW_RELEASE) {
|
||||||
|
glfwSetWindowShouldClose(windowHandle, true); // We will detect this in the rendering loop
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void pollEvents() {
|
||||||
|
glfwPollEvents();
|
||||||
|
}
|
||||||
|
|
||||||
|
protected void resized(int width, int height) {
|
||||||
|
this.width = width;
|
||||||
|
this.height = height;
|
||||||
|
try {
|
||||||
|
resizeFunc.call();
|
||||||
|
} catch (Exception excp) {
|
||||||
|
excp.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void update() {
|
||||||
|
glfwSwapBuffers(windowHandle);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean windowShouldClose() {
|
||||||
|
return glfwWindowShouldClose(windowHandle);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static class WindowOptions {
|
||||||
|
public boolean compatibleProfile;
|
||||||
|
public int fps;
|
||||||
|
public int height;
|
||||||
|
public int ups = Engine.TARGET_UPS;
|
||||||
|
public int width;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,4 +1,6 @@
|
|||||||
package org.example;
|
package org.xfe.engine;
|
||||||
|
|
||||||
|
import org.joml.Vector3f;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
|
||||||
@@ -6,14 +8,22 @@ public class World
|
|||||||
{
|
{
|
||||||
ArrayList<Entity> entities;
|
ArrayList<Entity> entities;
|
||||||
|
|
||||||
|
ArrayList<Light> lights;
|
||||||
|
|
||||||
public World()
|
public World()
|
||||||
{
|
{
|
||||||
this.entities = new ArrayList<>();
|
this.entities = new ArrayList<>();
|
||||||
|
this.lights = new ArrayList<>();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void addEntity(Entity e)
|
public void addEntity(Entity e)
|
||||||
{
|
{
|
||||||
this.entities.add(e);
|
this.entities.add(e);
|
||||||
}
|
}
|
||||||
|
public void addLight(Light l) {
|
||||||
|
this.lights.add(l);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void cleanup() {}
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,33 @@
|
|||||||
|
package org.xfe.game;
|
||||||
|
|
||||||
|
import org.xfe.engine.*;
|
||||||
|
|
||||||
|
public class Main implements GameLogic {
|
||||||
|
|
||||||
|
public static void main(String[] args) {
|
||||||
|
Main main = new Main();
|
||||||
|
Engine engine = new Engine("Test", new Window.WindowOptions(), main);
|
||||||
|
engine.start();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void cleanup() {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void init(Window window, World world, Render render) {
|
||||||
|
Entity cube = new Entity("/objs/cube.obj", "/shaders/shader.frag", "/shaders/shader.vert");
|
||||||
|
world.addEntity(cube);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void input(Window window, World world, long diffTimeMillis) {
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void update(Window window, World world, long diffTimeMillis) {
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -2,14 +2,14 @@
|
|||||||
out vec4 FragColor;
|
out vec4 FragColor;
|
||||||
|
|
||||||
|
|
||||||
uniform float light_power;
|
//uniform float light_power;
|
||||||
uniform vec3 lightColor;
|
//uniform vec3 lightColor;
|
||||||
uniform vec3 objectColor;
|
//uniform vec3 objectColor;
|
||||||
uniform vec3 viewPos;
|
//uniform vec3 viewPos;
|
||||||
|
|
||||||
in vec3 FragPos;
|
in vec3 FragPos;
|
||||||
in vec3 Normal;
|
//in vec3 Normal;
|
||||||
in vec3 LightPos;
|
//in vec3 LightPos;
|
||||||
|
|
||||||
// const float light_power = 12.0;
|
// const float light_power = 12.0;
|
||||||
const float ambientStrength = 0.2;
|
const float ambientStrength = 0.2;
|
||||||
@@ -18,35 +18,6 @@ const float screenGamma = 2.2; // Assume the monitor is calibrated to the sRGB c
|
|||||||
|
|
||||||
void main()
|
void main()
|
||||||
{
|
{
|
||||||
// FragColor = vec4(1.0f, 0.0f, 0.0f, 1.0f);
|
FragColor = vec4(1.0f, 0.0f, 0.0f, 1.0f);
|
||||||
|
|
||||||
vec3 lightDir = LightPos - FragPos;
|
|
||||||
float distance = length(lightDir);
|
|
||||||
vec3 norm = normalize(Normal);
|
|
||||||
vec3 ambient = ambientStrength * lightColor;
|
|
||||||
|
|
||||||
distance = distance * distance;
|
|
||||||
lightDir = normalize(lightDir);
|
|
||||||
|
|
||||||
float lambertian = max(dot(norm, lightDir), 0.0);
|
|
||||||
vec3 diffuse = lambertian * lightColor;
|
|
||||||
float specular = 0.0;
|
|
||||||
|
|
||||||
if (lambertian > 0.0)
|
|
||||||
{
|
|
||||||
vec3 viewDir = normalize(-FragPos);
|
|
||||||
|
|
||||||
vec3 halfDir = normalize(lightDir + viewDir);
|
|
||||||
float specAngle = max(dot(halfDir, norm), 0.0);
|
|
||||||
specular = pow(specAngle, shininess);
|
|
||||||
}
|
|
||||||
|
|
||||||
vec3 colorLinear = (ambient + (diffuse * light_power) + (specular * light_power)) * objectColor;
|
|
||||||
|
|
||||||
// vec3 colorGammaCorrected = pow(colorLinear, vec3(1.0 / screenGamma));
|
|
||||||
|
|
||||||
FragColor = vec4(colorLinear, 1.0);
|
|
||||||
|
|
||||||
// vec3 norm = normalize(Normal);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1,22 +1,23 @@
|
|||||||
#version 330 core
|
#version 330 core
|
||||||
layout (location = 0) in vec3 aPos;
|
layout (location = 0) in vec3 aPos;
|
||||||
layout (location = 1) in vec3 aNormal;
|
// layout (location = 1) in vec3 aNormal;
|
||||||
//layout (location = 1) in vec3 aColor;
|
//layout (location = 1) in vec3 aColor;
|
||||||
|
|
||||||
uniform mat4 model;
|
// uniform mat4 model;
|
||||||
uniform mat4 view;
|
// uniform mat4 view;
|
||||||
uniform mat4 projection;
|
uniform mat4 projection;
|
||||||
uniform vec3 lightPos;
|
// uniform vec3 lightPos;
|
||||||
|
|
||||||
out vec3 FragPos;
|
out vec3 FragPos;
|
||||||
out vec3 Normal;
|
// out vec3 Normal;
|
||||||
out vec3 LightPos;
|
// out vec3 LightPos;
|
||||||
|
|
||||||
void main()
|
void main()
|
||||||
{
|
{
|
||||||
gl_Position = projection * view * model * vec4(aPos, 1.0);
|
// * view * model
|
||||||
FragPos = vec3(view * model * vec4(aPos, 1.0));
|
gl_Position = projection * vec4(aPos, 1.0);
|
||||||
Normal = mat3(transpose(inverse(view * model))) * aNormal;
|
FragPos = vec3(vec4(aPos, 1.0));
|
||||||
LightPos = vec3(view * vec4(lightPos, 1.0));
|
// Normal = mat3(transpose(inverse(view * model))) * aNormal;
|
||||||
|
// LightPos = vec3(view * vec4(lightPos, 1.0));
|
||||||
}
|
}
|
||||||
|
|
||||||
Reference in new issue
Block a user